bitmovin-analytics 2.45.0 → 2.46.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.
@@ -1 +1 @@
1
- {"version":3,"file":"bitmovin-analytics-bitmovin-player.js","mappings":"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","sources":["webpack://bitmovin.analytics/webpack/universalModuleDefinition","webpack://bitmovin.analytics/./src/utils/Http.ts","webpack://bitmovin.analytics/./src/features/Feature.ts","webpack://bitmovin.analytics/./src/core/LongPlaytimeFilteringBackend.ts","webpack://bitmovin.analytics/./src/utils/CodecHelper.ts","webpack://bitmovin.analytics/./src/enums/Player.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/SpeedMeterAdapter.ts","webpack://bitmovin.analytics/./src/core/EventDispatcher.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/playerModule.ts","webpack://bitmovin.analytics/./src/core/SessionPersistenceHandler.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8AdModule.ts","webpack://bitmovin.analytics/./src/core/QueueBackend.ts","webpack://bitmovin.analytics/./src/utils/EventDebugging.ts","webpack://bitmovin.analytics/./src/utils/stringUtils.ts","webpack://bitmovin.analytics/./src/utils/Logger.ts","webpack://bitmovin.analytics/./src/utils/playerAugmentationUtils.ts","webpack://bitmovin.analytics/./src/core/NoOpBackend.ts","webpack://bitmovin.analytics/./src/enums/Event.ts","webpack://bitmovin.analytics/./src/core/RemoteBackend.ts","webpack://bitmovin.analytics/./src/utils/WindowEventTracker.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/bitmovin8/Bitmovin8AnalyticsStateMachine.ts","webpack://bitmovin.analytics/./node_modules/javascript-state-machine/state-machine.js","webpack://bitmovin.analytics/./src/adapters/internal/InternalAdapter.ts","webpack://bitmovin.analytics/./src/core/HeartbeatService.ts","webpack://bitmovin.analytics/./src/utils/uuidUtils.ts","webpack://bitmovin.analytics/./src/core/BackendFactory.ts","webpack://bitmovin.analytics/./src/utils/Queue.ts","webpack://bitmovin.analytics/./src/types/PlaybackInfo.ts","webpack://bitmovin.analytics/./src/enums/ErrorCode.ts","webpack://bitmovin.analytics/./src/core/LicenseCheckingBackend.ts","webpack://bitmovin.analytics/./src/enums/VideoStartFailedReason.ts","webpack://bitmovin.analytics/./src/enums/AdType.ts","webpack://bitmovin.analytics/./src/utils/ViewportTracker.ts","webpack://bitmovin.analytics/./src/core/Measure.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/bitmovin8AdapterSsaiApiSanitizeUtils.ts","webpack://bitmovin.analytics/./src/core/ssai/SsaiService.ts","webpack://bitmovin.analytics/./src/core/Analytics.ts","webpack://bitmovin.analytics/./src/enums/CDNProvider.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/bitmovin8PlayerTypes.ts","webpack://bitmovin.analytics/./src/types/AdSample.ts","webpack://bitmovin.analytics/./src/types/LicensingRequest.ts","webpack://bitmovin.analytics/./src/utils/Settings.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8Adapter.ts","webpack://bitmovin.analytics/./src/types/StateMachineCallbacks.ts","webpack://bitmovin.analytics/./src/core/SourceInfoFallbackService.ts","webpack://bitmovin.analytics/./src/utils/Version.ts","webpack://bitmovin.analytics/./src/utils/documentCookieUtils.ts","webpack://bitmovin.analytics/./src/utils/Utils.ts","webpack://bitmovin.analytics/./src/utils/BitmovinProgressiveSourceHelper.ts","webpack://bitmovin.analytics/./src/utils/LicenseCall.ts","webpack://bitmovin.analytics/./src/utils/AnalyticsCall.ts","webpack://bitmovin.analytics/./src/adapters/internal/ads/AdModuleAPI.ts","webpack://bitmovin.analytics/./src/types/CustomDataValues.ts","webpack://bitmovin.analytics/./src/utils/Converter.ts","webpack://bitmovin.analytics/./src/types/AdAnalyticsSample.ts","webpack://bitmovin.analytics/./src/enums/CastTech.ts","webpack://bitmovin.analytics/./src/core/SegmentTracker.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiApiUtils.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8InternalAdapter.ts","webpack://bitmovin.analytics/./src/core/VideoCompletionTracker.ts","webpack://bitmovin.analytics/./src/features/FeatureManager.ts","webpack://bitmovin.analytics/./src/types/AdBreakSample.ts","webpack://bitmovin.analytics/./src/core/SequenceNumberBackend.ts","webpack://bitmovin.analytics/./src/core/DebuggingBackend.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/HttpRequestTrackingAdapter.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/AnalyticsStateMachine.ts","webpack://bitmovin.analytics/./src/features/errordetails/ErrorDetailBackend.ts","webpack://bitmovin.analytics/./src/features/httprequesttracking/HttpRequestTracking.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiUtils.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/stateMachineUtils.ts","webpack://bitmovin.analytics/./src/utils/analyticsConfigUtils.ts","webpack://bitmovin.analytics/./src/utils/WebOSUtils.ts","webpack://bitmovin.analytics/./src/enums/PlayerSize.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/SegmentTrackerAdapter.ts","webpack://bitmovin.analytics/./src/core/AdAnalytics.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiEngagementInteractionData.ts","webpack://bitmovin.analytics/./src/features/errordetails/ErrorDetailTracking.ts","webpack://bitmovin.analytics/./src/core/DownloadSpeedMeter.ts","webpack://bitmovin.analytics/./src/core/QualityChangeService.ts","webpack://bitmovin.analytics/./src/enums/PageLoadType.ts","webpack://bitmovin.analytics/webpack/bootstrap","webpack://bitmovin.analytics/./src/bitmovin-analytics-bitmovin-player.ts"],"sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse if(typeof exports === 'object')\n\t\texports[\"bitmovin\"] = factory();\n\telse\n\t\troot[\"bitmovin\"] = root[\"bitmovin\"] || {}, root[\"bitmovin\"][\"analytics\"] = factory();\n})(self, function() {\nreturn ","import {logger} from './Logger';\n\nexport function post(url: string, body: any, callback: any, async = true): void {\n let xhttp: any;\n let isLegacyXDomainRequestUsed = false;\n\n if ((window as any).XDomainRequest) {\n // XDomainRequest is the only way of having an XHR that supports CORS in IE8 and 9. At the time of IE8,\n // Microsoft decided to come up with their own CORS XHR instead of the standard CORS XMLHttpRequest\n // which is now used in IE10.\n // Since IE10, XDomainRequest has been deprecated and since IE11 removed.\n xhttp = new (window as any).XDomainRequest();\n isLegacyXDomainRequestUsed = true;\n } else {\n xhttp = new XMLHttpRequest();\n }\n\n const responseCallback = () => {\n if (xhttp.readyState == XMLHttpRequest.DONE) {\n if (xhttp.responseText <= 0) {\n return;\n }\n\n const sampleResponse = JSON.parse(xhttp.responseText);\n\n callback(sampleResponse);\n }\n };\n\n if (isLegacyXDomainRequestUsed) {\n xhttp.onload = responseCallback;\n } else {\n xhttp.onreadystatechange = responseCallback;\n }\n\n try {\n xhttp.open('POST', url, async);\n\n // XDomainRequest restriction: No custom headers may be added to the request\n // https://learn.microsoft.com/en-us/archive/blogs/ieinternals/xdomainrequest-restrictions-limitations-and-workarounds\n if (!isLegacyXDomainRequestUsed) {\n xhttp.setRequestHeader('Content-Type', 'text/plain');\n }\n\n xhttp.send(JSON.stringify(body));\n } catch (e) {\n logger.error('Failed to send POST request.', e);\n }\n}\n","import {isNotNullish} from '../utils/Utils';\n\nimport {FeatureConfig} from './FeatureConfig';\n\nexport abstract class Feature<TConfigContainer, TConfig extends FeatureConfig> {\n private _config?: TConfig = undefined;\n private _isEnabled = true;\n\n get config(): TConfig | undefined {\n return this._config;\n }\n\n get isEnabled(): boolean {\n return this._isEnabled;\n }\n\n abstract reset(): void;\n abstract enabled(): void;\n abstract disabled(): void;\n abstract configured(authenticated: boolean, config?: TConfig): void;\n\n disable() {\n this._isEnabled = false;\n this.disabled();\n }\n\n configure(authenticated: boolean, configContainer?: TConfigContainer): TConfig | undefined {\n if (isNotNullish(configContainer)) {\n this._config = this.extractConfig(configContainer);\n }\n this.configured(authenticated, this._config);\n return this._config;\n }\n\n abstract extractConfig(configContainer: TConfigContainer): TConfig | undefined;\n}\n","import {Sample} from '../types/Sample';\nimport {isNullish} from '../utils/Utils';\n\nimport {Backend} from './Backend';\n\n/**\n * The `LongPlaytimeFilteringBackend` is a decorator class that filters out samples\n * where the `played` time exceeds a specified threshold.\n *\n * If a sample's `played` time surpasses the threshold, it is not forwarded to the next backend.\n * Otherwise, the sample is passed along to the next backend for further processing.\n *\n * @implements {Backend}\n */\nexport class LongPlaytimeFilteringBackend implements Backend {\n nextBackend: Backend;\n\n constructor(next: Backend) {\n this.nextBackend = next;\n }\n\n sendRequest(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: any) {\n this.nextBackend.sendAdRequest(sample);\n }\n\n private isPlayedAboveThreshold(sample: Sample): boolean {\n return (isNullish(sample.played) ? 0 : sample.played) >= 90000;\n }\n}\n","const videoFormatCodecMap: {[format: string]: string[]} = {\n avc: ['video/mp4; codecs=\"avc1.42000a\"'],\n vp9: ['video/mp4; codecs=\"vp09.00.50.08\"'],\n av1: ['video/mp4; codecs=\"av01.0.08M.08\"'],\n hevc: ['video/mp4; codecs=\"hev1.1.6.L93.B0\"'],\n};\n\nexport class CodecHelper {\n static get supportedVideoFormats(): string[] | undefined {\n if (!('MediaSource' in window)) {\n return undefined;\n }\n const codecs = Object.getOwnPropertyNames(videoFormatCodecMap).filter((format) =>\n videoFormatCodecMap[format].some((codec) => this.isCodecSupported(codec)),\n );\n return codecs;\n }\n\n static isCodecSupported(codec: string): boolean {\n if (!('MediaSource' in window)) {\n return false;\n }\n\n return MediaSource.isTypeSupported(codec);\n }\n}\n","export enum Player {\n AMAZON_IVS = 'amazonivs',\n BITMOVIN = 'bitmovin',\n BITMOVIN_PWX = 'bitmovin-pwx',\n CHROMECAST_SHAKA = 'chromecast-shaka',\n DASHJS = 'dashjs',\n HLSJS = 'hlsjs',\n HTML5 = 'html5',\n JW = 'jw',\n RADIANT = 'radiant',\n SHAKA = 'shaka',\n VIDEOJS = 'videojs',\n}\n","import type {PlayerAPI} from 'bitmovin-player';\n\nimport {DownloadSpeedMeter} from '../../../core/DownloadSpeedMeter';\n\nexport class SpeedMeterAdapter {\n private meter: DownloadSpeedMeter;\n\n constructor(player: PlayerAPI, meter: DownloadSpeedMeter) {\n this.meter = meter;\n player.on(player.exports.PlayerEvent.DownloadFinished, (event) => this.handleOnDownloadFinishEvent(event));\n }\n\n getDownloadSpeedMeter(): DownloadSpeedMeter {\n return this.meter;\n }\n\n handleOnDownloadFinishEvent(event: any) {\n if (!event.success) {\n return;\n }\n if (event.downloadType.indexOf('media/video') === 0) {\n this.meter.addMeasurement({\n duration: event.downloadTime,\n size: event.size,\n timeToFirstByte: event.timeToFirstByte,\n timestamp: new Date(),\n httpStatus: event.httpStatus,\n });\n }\n }\n}\n","export interface Subscribable<TArgs> {\n subscribe(callback: EventHandler<TArgs>): () => void;\n unsubscribe(callback: EventHandler<TArgs>);\n}\n\ntype EventHandler<TArgs> = (args: TArgs) => void;\n\nexport class EventDispatcher<TArgs> implements Subscribable<TArgs> {\n private callbacks: Array<EventHandler<TArgs>> = [];\n\n subscribe(callback: EventHandler<TArgs>): () => void {\n this.callbacks.push(callback);\n\n return () => this.unsubscribe(callback);\n }\n\n dispatch(args: TArgs) {\n const callbacks = this.callbacks.slice(0);\n callbacks.forEach((callback) => {\n callback(args);\n });\n }\n\n unsubscribe(callback: EventHandler<TArgs>) {\n const index = this.callbacks.indexOf(callback);\n if (index > -1) {\n this.callbacks.splice(index, 1);\n }\n }\n\n get subscriberCount() {\n return this.callbacks.length;\n }\n}\n","import {Bitmovin8Adapter} from './Bitmovin8Adapter';\n\n/*\n * @see https://github.com/bitmovin-engineering/bitdash/blob/ccd3227dac82d1416a471711b40ee0f65d7f9ddb/src/ModuleDefinition.ts#L17\n */\nexport const PlayerModule = {\n name: 'analytics',\n module: {\n Analytics: Bitmovin8Adapter,\n },\n hooks: {\n setup: (module: any, player: any) => {\n const config = player.getConfig();\n const isConfigMissing = !config;\n const isAnalyticsDisabled = config?.analytics === false;\n\n if (isConfigMissing || isAnalyticsDisabled) {\n return Promise.resolve();\n }\n\n const analyticsBitmovin8Adapter = module.Analytics;\n const analyticsModuleInstance = new analyticsBitmovin8Adapter(player);\n return Promise.resolve(analyticsModuleInstance);\n },\n },\n} as const;\n","import type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport {deleteCookie, getCookie, setCookie} from '../utils/documentCookieUtils';\nimport {isBlank, isValidString} from '../utils/stringUtils';\nimport {isNullish, isNumber} from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\n\nexport const COOKIE_NAME_BITMOVIN_ANALYTICS_UUID = 'bitmovin_analytics_uuid';\n/** One year in seconds */\nexport const COOKIE_DEFAULT_MAX_AGE = 365 * 24 * 60 * 60;\n\nexport class SessionPersistenceHandler {\n readonly userId: string;\n\n constructor(config: AnalyticsConfig) {\n const collectorConfig = config.config;\n\n const shouldNotUseCookies = collectorConfig?.cookiesEnabled === false;\n\n if (shouldNotUseCookies) {\n deleteCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID);\n this.userId = generateUUID();\n return;\n }\n\n const existingUserId = getCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID);\n this.userId = !isBlank(existingUserId) ? existingUserId : generateUUID();\n\n const cookieDomain = validateCookieDomainValue(collectorConfig?.cookiesDomain);\n const cookieMaxAge = validateCookieMaxAgeValue(collectorConfig?.cookiesMaxAge);\n\n // we set also expires, because max-age is not supported on old browsers like IE8\n const nowMillis = Date.now();\n const expirationDate = new Date(nowMillis + cookieMaxAge * 1000);\n const cookieExpires = expirationDate.toUTCString();\n\n setCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID, this.userId, {\n domain: cookieDomain,\n expires: cookieExpires,\n maxAge: cookieMaxAge,\n });\n }\n}\n\nexport const validateCookieDomainValue = (value: unknown): string | undefined => {\n if (isNullish(value)) {\n return undefined;\n }\n\n if (!isValidString(value)) {\n return undefined;\n }\n\n if (isBlank(value)) {\n return undefined;\n }\n\n return encodeURIComponent(value);\n};\n\nexport const validateCookieMaxAgeValue = (value: unknown): number => {\n if (isNullish(value)) {\n return COOKIE_DEFAULT_MAX_AGE;\n }\n\n if (!isNumber(value)) {\n return COOKIE_DEFAULT_MAX_AGE;\n }\n\n return value;\n};\n","import type {PlayerAPI, UserInteractionEvent} from 'bitmovin-player';\n\nimport {WindowEventTracker} from '../../utils/WindowEventTracker';\nimport {AdCallbacks, AdModuleAPI} from '../internal/ads/AdModuleAPI';\n\nexport class Bitmovin8AdModule implements AdModuleAPI {\n adCallbacks = new AdCallbacks();\n\n constructor(\n private player: PlayerAPI,\n private windowEventTracker: WindowEventTracker,\n ) {\n this.register();\n }\n\n isLinearAdActive = () => {\n if (this.player.ads) {\n return (this.player.ads as any).isLinearAdActive() || false;\n }\n return false;\n };\n getContainer = () => this.player.getContainer();\n getAdModuleInfo = () => {\n if (this.player.ads) {\n return (this.player.ads as any).getModuleInfo();\n }\n return {name: undefined, version: undefined};\n };\n currentTime = () => this.player.getCurrentTime();\n\n private register() {\n this.player.on(this.player.exports.PlayerEvent.Play, (e: UserInteractionEvent) => {\n if (e.issuer === 'advertising-api') {\n this.adCallbacks.onPlay(e.issuer);\n }\n });\n this.player.on(this.player.exports.PlayerEvent.Paused, (e: UserInteractionEvent) => {\n if (e.issuer === 'advertising-api') {\n this.adCallbacks.onPause(e.issuer);\n }\n });\n this.player.on(this.player.exports.PlayerEvent.AdStarted, (event: any) => {\n this.adCallbacks.onAdStarted(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdFinished, (event: any) => {\n this.adCallbacks.onAdFinished(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdBreakStarted, (event: any) => {\n this.adCallbacks.onAdBreakStarted(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdBreakFinished, (event: any) => {\n this.adCallbacks.onAdBreakFinished(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdClicked, (event: any) => {\n this.adCallbacks.onAdClicked(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdQuartile, (event: any) => {\n this.adCallbacks.onAdQuartile(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdSkipped, (event: any) => {\n this.adCallbacks.onAdSkipped(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdError, (event: any) => {\n this.adCallbacks.onAdError(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdManifestLoaded, (event: any) => {\n this.adCallbacks.onAdManifestLoaded(event);\n });\n const handlePageClose = () => {\n this.adCallbacks.onBeforeUnload();\n };\n this.windowEventTracker.addEventListener('beforeunload', handlePageClose);\n this.windowEventTracker.addEventListener('unload', handlePageClose);\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\n\nimport {Backend} from './Backend';\n\n/**\n * The `QueueBackend` class is responsible for queuing samples for deferred processing.\n * Samples are stored in different queues depending on the sample type and can be flushed\n * to another backend for further processing.\n *\n * This is useful e.g. to still collect sample data while waiting for a license call to succeed.\n *\n * @implements {Backend}\n */\nexport class QueueBackend implements Backend {\n queue: Sample[] = [];\n unloadQueue: Sample[] = [];\n syncQueue: Sample[] = [];\n adQueue: Array<AdAnalyticsSample & AdBreakSample & AdSample> = [];\n\n sendRequest(sample: Sample) {\n this.queue.push(sample);\n }\n sendUnloadRequest(sample: Sample) {\n this.unloadQueue.push(sample);\n }\n sendRequestSynchronous(sample: Sample) {\n this.syncQueue.push(sample);\n }\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.adQueue.push(sample);\n }\n\n flushTo(backend: Backend) {\n this.queue.forEach((e) => {\n backend.sendRequest(e);\n });\n this.unloadQueue.forEach((e) => {\n backend.sendUnloadRequest(e);\n });\n this.syncQueue.forEach((e) => {\n backend.sendRequestSynchronous(e);\n });\n this.adQueue.forEach((e) => {\n backend.sendAdRequest(e);\n });\n }\n}\n","export class EventDebugging {\n event: string | undefined;\n from: string | undefined;\n to: string | undefined;\n timestamp: number;\n eventObject: any;\n\n constructor(\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n timestamp: number,\n eventObject: any,\n ) {\n this.event = event;\n this.from = from;\n this.to = to;\n this.timestamp = timestamp;\n this.eventObject = eventObject;\n }\n}\n","import {isNotNullish, isNullish} from './Utils';\n\nexport const isValidString = (s: unknown): s is string => isNotNullish(s) && typeof s === 'string';\n\nexport const isEmpty = (s: string | null | undefined): boolean => isNullish(s) || s.length === 0;\n\nexport const isBlank = (s: string | null | undefined): boolean => isEmpty(s) || isEmpty(s?.trim());\n\nexport const endsWith = (s: string, suffix: string): boolean => {\n if (!isValidString(s) || !isValidString(suffix)) {\n return false;\n }\n\n // our target is ES5, so we can't use String.prototype.endsWith without checking for it\n if (isNotNullish(String.prototype.endsWith)) {\n return s.endsWith(suffix);\n }\n\n return s.substring(s.length - suffix.length) === suffix;\n};\n\nexport const startsWith = (s: string, prefix: string): boolean => {\n if (!isValidString(s) || !isValidString(prefix)) {\n return false;\n }\n\n // our target is ES5, so we can't use String.prototype.startsWith without checking for it\n if (isNotNullish(String.prototype.startsWith)) {\n return s.startsWith(prefix);\n }\n return s.substring(0, prefix.length) === prefix;\n};\n","import {AnalyticsConfig} from '../types/AnalyticsConfig';\n\n/**\n * Uses a Singleton design pattern.\n *\n * We want to ensure that only one object of its kind exists and provides a single point of access to it,\n * to be able to control enabled/disabled `console` logs for customer in whole code base.\n */\nclass Logger {\n private static instance: Logger;\n\n static getInstance(): Logger {\n if (!Logger.instance) {\n Logger.instance = new Logger();\n }\n\n return Logger.instance;\n }\n\n private analyticsDebugConfig: Readonly<AnalyticsConfig['debug']>;\n\n private constructor() {}\n\n initialize(analyticsDebugConfig: AnalyticsConfig['debug']) {\n this.analyticsDebugConfig = analyticsDebugConfig;\n }\n\n //#region Console API\n log(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.log(message, optionalParams); //eslint-disable-line no-console\n }\n\n table(tabularData: unknown, properties?: readonly string[]) {\n if (!this.enabled) {\n return;\n }\n console.table(tabularData, properties); //eslint-disable-line no-console\n }\n\n warn(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.warn(message, optionalParams); //eslint-disable-line no-console\n }\n\n error(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.error(message, optionalParams); //eslint-disable-line no-console\n }\n\n /**\n * Outputs an error message to user/customer console.\n *\n * Does not relay on {@link Logger#enabled}! because it should deliver the error information to user/customer.\n */\n errorMessageToUser(message?: unknown, ...optionalParams: unknown[]) {\n console.error(message, ...optionalParams); //eslint-disable-line no-console\n }\n //#endregion\n\n /** `true` if {@link AnalyticsConfig#debug} was set */\n private get enabled() {\n return (this.analyticsDebugConfig as boolean) || false;\n }\n}\n\nexport const padRight = (str: string | undefined, length: number) => {\n const padStr = new Array(length).join(' ');\n return (str + padStr).slice(0, length);\n};\n\nexport const logger = Logger.getInstance();\n","import type {InternalAdapterAPI} from '../adapters/internal/InternalAdapterAPI';\nimport type {Analytics} from '../core/Analytics';\n\nimport {logger} from './Logger';\nimport {isNullish} from './Utils';\n\nexport const BITMOVIN_ANALYTICS_AUGMENTED_MARKER = '__bitmovinAnalyticsHasBeenSetup';\n\n/**\n * Checks if analytics has already been initialized on this player instance,\n * aka. if {@link BITMOVIN_ANALYTICS_AUGMENTED_MARKER} is present on the player instance.\n *\n * @param player\n */\nexport function hasPlayerAlreadyBeenAugmented(player: any): boolean {\n return player[BITMOVIN_ANALYTICS_AUGMENTED_MARKER] === true;\n}\n\n/**\n * Marks the player instance as already instrumented by analytics,\n * aka. sets {@link BITMOVIN_ANALYTICS_AUGMENTED_MARKER} on the player instance.\n */\nexport function markPlayerInstanceAsAugmented(player: any) {\n player[BITMOVIN_ANALYTICS_AUGMENTED_MARKER] = true;\n}\n\n/**\n * In context of player augmentation, if player was already augmented, adapter properties\n * {@link Analytics} or {@link InternalAdapterAPI} will stay `undefined`, this type guard\n * is utility to help us check if the instance is defined.\n */\nexport function isDefined<T extends Analytics | InternalAdapterAPI>(instance: T | null | undefined): instance is T {\n if (isNullish(instance)) {\n logger.log(\"Bitmovin Analytics: Adapter hasn't been initialized yet\");\n return false;\n }\n\n return true;\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\n\nimport {Backend} from './Backend';\n\n/**\n * The `NoOpBackend` is a no-operation implementation of the `Backend` interface.\n * It serves as a placeholder backend when the actual `Backend` functionality is disabled or not required.\n * E.g. in scenarios such as releasing the adapter or when the Collector is disabled via {@link CollectorConfig#enabled}.\n *\n * Using `NoOpBackend` ensures that the code does not need to handle cases where `Backend` might be undefined,\n * thereby simplifying the logic and reducing the need for null or undefined checks.\n *\n * @implements {Backend}\n */\nexport class NoOpBackend implements Backend {\n sendRequest(_sample: Sample) {\n // empty\n }\n sendUnloadRequest(_sample: Sample) {\n // empty\n }\n sendRequestSynchronous(_sample: Sample) {\n // empty\n }\n sendAdRequest(_sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n // empty\n }\n}\n","import {\n AnalyticsEventBase,\n AudioChangeEvent,\n ErrorEvent,\n SourceChangeEvent,\n VideoChangeEvent,\n} from '../types/EventData';\n\n/**\n * If we specify the name of our initial state, then an implicit 'startup' initial event will be created by JSM\n * and fired when the state machine is constructed.\n *\n * Because that implicit JSM initial event is called 'startup', it could cause confusion with our \"STARTUP state\", so for\n * that reason we will use custom JSM initial event name, to be able to distinguish it from our other {@link Event}s.\n *\n * This event should not be used in the application code, it is only used by the JSM library!\n *\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#initialization-options\n */\nexport const JSM_INITIAL_EVENT = 'jsm-initial';\n\nexport enum Event {\n AUDIO_CHANGE = 'audioChange',\n AUDIOTRACK_CHANGED = 'audioTrackChanged',\n CUSTOM_DATA_CHANGE = 'customDataChange',\n /**\n * Fired when the player has finished playback.\n */\n END = 'end',\n END_AD = 'adEnd',\n END_BUFFERING = 'endBuffering',\n END_CAST = 'endCasting',\n END_FULLSCREEN = 'endFullscreen',\n ERROR = 'playerError',\n MANUAL_SOURCE_CHANGE = 'manualSourceChangeInitiated',\n MUTE = 'mute',\n PAUSE = 'pause',\n PLAY = 'play',\n PLAYING = 'playing',\n /**\n * Used only by the CAFv3 adapter\n */\n PLAYLIST_TRANSITION = 'playlistTransition',\n /**\n * Fired when the player is ready to play.\n */\n READY = 'ready',\n SCREEN_RESIZE = 'resize',\n SEEK = 'seek',\n SEEKED = 'seeked',\n SOURCE_LOADED = 'sourceLoaded',\n SOURCE_UNLOADED = 'sourceUnloaded',\n START_AD = 'adStart',\n START_BUFFERING = 'startBuffering',\n START_CAST = 'startCasting',\n START_FULLSCREEN = 'startFullscreen',\n SUBTITLE_CHANGE = 'subtitleChange',\n TIMECHANGED = 'timechanged',\n UN_MUTE = 'unMute',\n /**\n * Fired when page with player is closed or when the player is unloaded/destroyed.\n */\n UNLOAD = 'unload',\n VIDEO_CHANGE = 'videoChange',\n VIDEOSTART_TIMEOUT = 'VIDEOSTART_TIMEOUT',\n}\n\nexport interface EventMap {\n [Event.READY]: AnalyticsEventBase;\n [Event.SOURCE_LOADED]: AnalyticsEventBase;\n [Event.PLAY]: AnalyticsEventBase;\n [Event.PLAYING]: AnalyticsEventBase;\n [Event.PAUSE]: AnalyticsEventBase;\n [Event.TIMECHANGED]: AnalyticsEventBase;\n [Event.SEEK]: AnalyticsEventBase;\n [Event.SEEKED]: AnalyticsEventBase;\n [Event.START_CAST]: AnalyticsEventBase;\n [Event.END_CAST]: AnalyticsEventBase;\n [Event.START_BUFFERING]: AnalyticsEventBase;\n [Event.END_BUFFERING]: AnalyticsEventBase;\n [Event.AUDIOTRACK_CHANGED]: AnalyticsEventBase;\n [Event.AUDIO_CHANGE]: AudioChangeEvent;\n [Event.VIDEO_CHANGE]: VideoChangeEvent;\n [Event.START_FULLSCREEN]: AnalyticsEventBase;\n [Event.END_FULLSCREEN]: AnalyticsEventBase;\n [Event.START_AD]: AnalyticsEventBase;\n [Event.SUBTITLE_CHANGE]: AnalyticsEventBase;\n [Event.END_AD]: AnalyticsEventBase;\n [Event.MUTE]: AnalyticsEventBase;\n [Event.UN_MUTE]: AnalyticsEventBase;\n [Event.ERROR]: ErrorEvent;\n [Event.SCREEN_RESIZE]: AnalyticsEventBase;\n [Event.UNLOAD]: AnalyticsEventBase;\n [Event.END]: AnalyticsEventBase;\n [Event.SOURCE_UNLOADED]: AnalyticsEventBase;\n [Event.MANUAL_SOURCE_CHANGE]: SourceChangeEvent;\n [Event.VIDEOSTART_TIMEOUT]: AnalyticsEventBase;\n [Event.CUSTOM_DATA_CHANGE]: AnalyticsEventBase;\n [Event.PLAYLIST_TRANSITION]: AnalyticsEventBase;\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {AnalyticsCall} from '../utils/AnalyticsCall';\nimport {noOp} from '../utils/Utils';\n\nimport {Backend} from './Backend';\n\n/**\n * The `RemoteBackend` class is responsible for actually sending out the samples using the {@link AnalyticsCall} class.\n * Before each sample is sent, the `RemoteBackend` attaches a license key to the sample.\n *\n * @implements {Backend}\n */\nexport class RemoteBackend implements Backend {\n analyticsCall: AnalyticsCall;\n hasAdModule: boolean;\n\n constructor(\n hasAdModule: boolean,\n backendBaseUrl: string,\n private licenseKey: string,\n ) {\n this.hasAdModule = hasAdModule;\n this.analyticsCall = new AnalyticsCall(backendBaseUrl);\n }\n\n sendRequest(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendRequest(sample, noOp);\n }\n\n sendUnloadRequest(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendRequestSynchronous(sample, noOp);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n sample.key = this.licenseKey;\n if (!this.hasAdModule) {\n return;\n }\n this.analyticsCall.sendAdRequest(sample);\n }\n}\n","interface EventListener {\n eventName: string;\n func: EventListenerOrEventListenerObject;\n}\n\nexport class WindowEventTracker {\n private trackedObjects: EventListener[] = [];\n\n addEventListener(eventName: string, func: EventListenerOrEventListenerObject) {\n this.trackedObjects.push({eventName, func});\n window.addEventListener(eventName, func);\n }\n\n release() {\n while (this.trackedObjects.length !== 0) {\n const obj = this.trackedObjects.pop();\n if (obj === undefined) {\n continue;\n }\n\n window.removeEventListener(obj.eventName, obj.func);\n }\n }\n}\n","import * as StateMachine from 'javascript-state-machine';\n\nimport {HeartbeatService} from '../../core/HeartbeatService';\nimport {Event, JSM_INITIAL_EVENT} from '../../enums/Event';\nimport {createVideoStartFailedReason} from '../../enums/VideoStartFailedReason';\nimport type {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {AnalyticsEventBase, ErrorEvent} from '../../types/EventData';\nimport type {StateMachineCallbacks} from '../../types/StateMachineCallbacks';\nimport {EventDebugging} from '../../utils/EventDebugging';\nimport {logger} from '../../utils/Logger';\nimport {isNumber, noOp} from '../../utils/Utils';\nimport {AnalyticsStateMachine} from '../AnalyticsStateMachine';\nimport {\n customStateMachineErrorCallback,\n logMissingCallbackWarning,\n logStateMachineTransition,\n on,\n} from '../stateMachineUtils';\n\nenum State {\n AD_PAUSE = 'AD_PAUSE',\n AD_PLAYING = 'AD_PLAYING',\n AD_READY = 'AD_READY',\n /** This event is called when an ad is played directly after the player startup phase */\n AD_STARTUP = 'AD_STARTUP',\n AUDIOTRACK_CHANGING = 'AUDIOTRACK_CHANGING',\n CASTING = 'CASTING',\n CUSTOMDATACHANGE = 'CUSTOMDATACHANGE',\n END = 'END',\n /** see {@link State.PLAY_SEEKING} */\n END_PLAY_SEEKING = 'END_PLAY_SEEKING',\n ERROR = 'ERROR',\n INITIAL_SOURCE_CHANGE = 'INITIAL_SOURCE_CHANGE',\n MUTING_PAUSE = 'MUTING_PAUSE',\n MUTING_PLAY = 'MUTING_PLAY',\n MUTING_READY = 'MUTING_READY',\n PAUSE = 'PAUSE',\n /**\n * THE Seeking state.\n * Seeking tracking = time spend in PLAY_SEEKING + END_PLAY_SEEKING.\n * - PLAY_SEEKING - THE seeking state for tracking time spend in seeking.\n * - END_PLAY_SEEKING - part of seeking time, where we wait `in between` seeking and continuing with other states.\n * - usually we are in this state when holding the mouse while seeking -> this will produce multiple connected seeks.\n */\n PLAY_SEEKING = 'PLAY_SEEKING',\n PLAYING = 'PLAYING',\n QUALITYCHANGE = 'QUALITYCHANGE',\n QUALITYCHANGE_PAUSE = 'QUALITYCHANGE_PAUSE',\n QUALITYCHANGE_REBUFFERING = 'QUALITYCHANGE_REBUFFERING',\n READY = 'READY',\n REBUFFERING = 'REBUFFERING',\n SETUP = 'SETUP',\n SOURCE_CHANGING = 'SOURCE_CHANGING',\n STARTUP = 'STARTUP',\n SUBTITLE_CHANGING = 'SUBTITLE_CHANGING',\n VIDEOSTART_FAILED = 'VIDEOSTART_FAILED',\n}\n\nexport class Bitmovin8AnalyticsStateMachine extends AnalyticsStateMachine {\n private debuggingStates: EventDebugging[] = [];\n private enabledDebugging = false;\n\n private seekStartTimestamp: number | undefined;\n // used for ads, because when AdFinished event is fired and call to state machine is made\n // data form player indicate that video is playing from beginning even if ad is in middle of video\n private lastTrackedVideoEndObject?: AnalyticsEventBase;\n\n constructor(\n stateMachineCallbacks: StateMachineCallbacks,\n playingHeartbeatService: HeartbeatService,\n opts: AnalyticsStateMachineOptions,\n ) {\n super(stateMachineCallbacks, playingHeartbeatService, opts);\n }\n\n getAllStatesBut(states: string[]) {\n return this.getAllStates().filter((i) => states.indexOf(i) < 0);\n }\n\n getAllStates() {\n return Object.keys(State).map((key) => State[key]);\n }\n\n override createStateMachine(opts: AnalyticsStateMachineOptions): StateMachine.StateMachine {\n return StateMachine.create({\n // custom initial state and custom JSM initial event name\n // initial event is used by JSM for the initial state transition 'none' -> 'SETUP'\n initial: {state: State.SETUP, event: JSM_INITIAL_EVENT},\n error: customStateMachineErrorCallback,\n events: [\n {\n name: Event.SOURCE_LOADED,\n from: [State.SETUP, State.ERROR, State.SOURCE_CHANGING, State.INITIAL_SOURCE_CHANGE],\n to: State.READY,\n },\n\n {name: Event.PLAY, from: State.READY, to: State.STARTUP},\n {name: Event.PLAYING, from: State.READY, to: State.PLAYING},\n on(Event.READY).stayIn(State.READY),\n on(Event.VIDEO_CHANGE).stayIn(State.READY),\n on(Event.AUDIO_CHANGE).stayIn(State.READY),\n\n {name: Event.ERROR, from: [State.STARTUP, State.AD_STARTUP], to: State.VIDEOSTART_FAILED},\n {name: Event.UNLOAD, from: [State.STARTUP, State.AD_STARTUP], to: State.VIDEOSTART_FAILED},\n {name: Event.VIDEOSTART_TIMEOUT, from: State.STARTUP, to: State.VIDEOSTART_FAILED},\n\n on(Event.PLAY).stayIn(State.STARTUP),\n on(Event.PLAYING).stayIn(State.STARTUP),\n {name: Event.TIMECHANGED, from: State.STARTUP, to: State.PLAYING},\n on(Event.START_BUFFERING).stayIn(State.STARTUP),\n on(Event.END_BUFFERING).stayIn(State.STARTUP),\n on(Event.VIDEO_CHANGE).stayIn(State.STARTUP),\n on(Event.AUDIO_CHANGE).stayIn(State.STARTUP),\n on(Event.READY).stayIn(State.STARTUP),\n {name: Event.PAUSE, from: State.STARTUP, to: State.READY},\n\n on(Event.PLAYING).stayIn(State.PLAYING),\n on(Event.TIMECHANGED).stayIn(State.PLAYING),\n on(Event.END_BUFFERING).stayIn(State.PLAYING),\n {name: Event.START_BUFFERING, from: State.PLAYING, to: State.REBUFFERING},\n {name: Event.END_BUFFERING, from: State.REBUFFERING, to: State.PLAYING},\n on(Event.TIMECHANGED).stayIn(State.REBUFFERING),\n\n {name: Event.PAUSE, from: State.PLAYING, to: State.PAUSE},\n {name: Event.PAUSE, from: State.REBUFFERING, to: State.PAUSE},\n {name: Event.PLAY, from: State.PAUSE, to: State.PLAYING},\n\n {name: Event.VIDEO_CHANGE, from: State.PLAYING, to: State.QUALITYCHANGE},\n {name: Event.AUDIO_CHANGE, from: State.PLAYING, to: State.QUALITYCHANGE},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE),\n {name: 'FINISH_QUALITYCHANGE', from: State.QUALITYCHANGE, to: State.PLAYING},\n\n {name: Event.VIDEO_CHANGE, from: State.PAUSE, to: State.QUALITYCHANGE_PAUSE},\n {name: Event.AUDIO_CHANGE, from: State.PAUSE, to: State.QUALITYCHANGE_PAUSE},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE_PAUSE),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE_PAUSE),\n {name: 'FINISH_QUALITYCHANGE_PAUSE', from: State.QUALITYCHANGE_PAUSE, to: State.PAUSE},\n\n //#region Seeking\n\n // start seeking\n {name: Event.SEEK, from: State.PLAYING, to: State.PLAY_SEEKING},\n\n // mark the seeked as finished\n {name: Event.PLAY, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n {name: Event.PLAYING, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n {name: Event.SEEKED, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n\n // seek while previous seek not completed\n {name: Event.SEEK, from: State.END_PLAY_SEEKING, to: State.PLAY_SEEKING},\n\n // seek completely finished and cont playing\n {name: Event.PLAYING, from: State.END_PLAY_SEEKING, to: State.PLAYING},\n {name: Event.TIMECHANGED, from: State.END_PLAY_SEEKING, to: State.PLAYING},\n\n // if PAUSE happens during the seeking (or at the end of seeking) we need to transition to PAUSE state\n {name: Event.PAUSE, from: [State.PLAY_SEEKING, State.END_PLAY_SEEKING], to: State.PAUSE},\n\n //#region Seeking disabled transitions\n // ignore transitions in PLAY_SEEKING\n on(Event.SEEK).stayIn(State.PLAY_SEEKING),\n on(Event.AUDIO_CHANGE).stayIn(State.PLAY_SEEKING),\n on(Event.VIDEO_CHANGE).stayIn(State.PLAY_SEEKING),\n on(Event.START_BUFFERING).stayIn(State.PLAY_SEEKING),\n on(Event.END_BUFFERING).stayIn(State.PLAY_SEEKING),\n\n // ignore transitions in END_PLAY_SEEKING\n on(Event.START_BUFFERING).stayIn(State.END_PLAY_SEEKING),\n on(Event.END_BUFFERING).stayIn(State.END_PLAY_SEEKING),\n on(Event.SEEKED).stayIn(State.END_PLAY_SEEKING),\n on(Event.PLAY).stayIn(State.END_PLAY_SEEKING),\n\n // ignore Seek events during PAUSE\n on(Event.SEEK).stayIn(State.PAUSE),\n on(Event.SEEKED).stayIn(State.PAUSE),\n\n // ignore seeked during Playing because of not allowed keyboard seeking\n on(Event.SEEKED).stayIn(State.PLAYING),\n //#endregion Seeking disabled transitions\n\n //#endregion Seeking\n\n {name: Event.END, from: State.PLAY_SEEKING, to: State.END},\n {name: Event.END, from: State.PLAYING, to: State.END},\n {name: Event.END, from: State.PAUSE, to: State.END},\n\n on(Event.SEEK).stayIn(State.END),\n on(Event.SEEKED).stayIn(State.END),\n on(Event.TIMECHANGED).stayIn(State.END),\n on(Event.END_BUFFERING).stayIn(State.END),\n on(Event.START_BUFFERING).stayIn(State.END),\n on(Event.END).stayIn(State.END),\n\n {name: Event.PLAY, from: State.END, to: State.STARTUP},\n\n {name: Event.ERROR, from: this.getAllStatesBut([State.STARTUP]), to: State.ERROR},\n\n {name: Event.UNLOAD, from: this.getAllStatesBut([State.STARTUP, State.AD_STARTUP]), to: State.END},\n\n {name: Event.CUSTOM_DATA_CHANGE, from: [State.PLAYING, State.PAUSE], to: State.CUSTOMDATACHANGE},\n {name: Event.PLAYING, from: State.CUSTOMDATACHANGE, to: State.PLAYING},\n {name: Event.PAUSE, from: State.CUSTOMDATACHANGE, to: State.PAUSE},\n\n {name: Event.SUBTITLE_CHANGE, from: State.PLAYING, to: State.SUBTITLE_CHANGING},\n on(Event.SUBTITLE_CHANGE).stayIn(State.PAUSE),\n on(Event.SUBTITLE_CHANGE).stayIn(State.REBUFFERING),\n on(Event.SUBTITLE_CHANGE).stayIn(State.END_PLAY_SEEKING),\n on(Event.SUBTITLE_CHANGE).stayIn(State.SUBTITLE_CHANGING),\n {name: Event.TIMECHANGED, from: State.SUBTITLE_CHANGING, to: State.PLAYING},\n\n {name: Event.AUDIOTRACK_CHANGED, from: State.PLAYING, to: State.AUDIOTRACK_CHANGING},\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.PAUSE),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.REBUFFERING),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.END_PLAY_SEEKING),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.AUDIOTRACK_CHANGING),\n {name: Event.TIMECHANGED, from: State.AUDIOTRACK_CHANGING, to: State.PLAYING},\n\n // #region Ads\n {name: Event.START_AD, from: State.STARTUP, to: State.AD_STARTUP},\n {name: Event.END_AD, from: State.AD_STARTUP, to: State.STARTUP},\n on(Event.PLAY).stayIn(State.AD_STARTUP),\n on(Event.PAUSE).stayIn(State.AD_STARTUP),\n\n {name: Event.START_AD, from: State.READY, to: State.AD_READY},\n /** After the pre-rolls, the main content will always start playing, no matter if autoplay: true/false */\n {name: Event.END_AD, from: State.AD_READY, to: State.STARTUP},\n on(Event.PLAY).stayIn(State.AD_READY),\n on(Event.PAUSE).stayIn(State.AD_READY),\n\n {name: Event.START_AD, from: State.PAUSE, to: State.AD_PAUSE},\n {name: Event.END_AD, from: State.AD_PAUSE, to: State.PAUSE},\n on(Event.PLAY).stayIn(State.AD_PAUSE),\n on(Event.PAUSE).stayIn(State.AD_PAUSE),\n\n {name: Event.START_AD, from: State.PLAYING, to: State.AD_PLAYING},\n {name: Event.END_AD, from: State.AD_PLAYING, to: State.PLAYING},\n on(Event.PLAY).stayIn(State.AD_PLAYING),\n on(Event.PAUSE).stayIn(State.AD_PLAYING),\n {name: Event.END, from: State.AD_PLAYING, to: State.END},\n\n // Ignore timechanged events during ads\n on(Event.TIMECHANGED).stayIn(State.AD_STARTUP),\n on(Event.TIMECHANGED).stayIn(State.AD_READY),\n on(Event.TIMECHANGED).stayIn(State.AD_PAUSE),\n on(Event.TIMECHANGED).stayIn(State.AD_PLAYING),\n\n // Ignore End Ad events when no ad has started\n on(Event.END_AD).stayIn(State.PLAYING),\n on(Event.END_AD).stayIn(State.PAUSE),\n on(Event.END_AD).stayIn(State.READY),\n on(Event.END_AD).stayIn(State.STARTUP),\n // #endregion\n\n {name: Event.MUTE, from: State.READY, to: State.MUTING_READY},\n {name: Event.UN_MUTE, from: State.READY, to: State.MUTING_READY},\n {name: 'FINISH_MUTING', from: State.MUTING_READY, to: State.READY},\n\n {name: Event.MUTE, from: State.PLAYING, to: State.MUTING_PLAY},\n {name: Event.UN_MUTE, from: State.PLAYING, to: State.MUTING_PLAY},\n {name: 'FINISH_MUTING', from: State.MUTING_PLAY, to: State.PLAYING},\n\n {name: Event.MUTE, from: State.PAUSE, to: State.MUTING_PAUSE},\n {name: Event.UN_MUTE, from: State.PAUSE, to: State.MUTING_PAUSE},\n {name: 'FINISH_MUTING', from: State.MUTING_PAUSE, to: State.PAUSE},\n\n {name: Event.START_CAST, from: [State.READY, State.PAUSE, State.PLAYING], to: State.CASTING},\n on(Event.PAUSE).stayIn(State.CASTING),\n on(Event.PLAY).stayIn(State.CASTING),\n on(Event.PLAYING).stayIn(State.CASTING),\n on(Event.TIMECHANGED).stayIn(State.CASTING),\n on(Event.MUTE).stayIn(State.CASTING),\n on(Event.UN_MUTE).stayIn(State.CASTING),\n on(Event.SEEK).stayIn(State.CASTING),\n on(Event.SEEKED).stayIn(State.CASTING),\n {name: Event.END_CAST, from: State.CASTING, to: State.READY},\n\n on(Event.SEEK).stayIn(State.READY),\n on(Event.SEEKED).stayIn(State.READY),\n on(Event.SEEKED).stayIn(State.STARTUP),\n\n {name: Event.MANUAL_SOURCE_CHANGE, from: this.getAllStatesBut([State.SETUP]), to: State.SOURCE_CHANGING},\n {name: Event.MANUAL_SOURCE_CHANGE, from: State.SETUP, to: State.INITIAL_SOURCE_CHANGE},\n {name: Event.SOURCE_UNLOADED, from: this.getAllStates(), to: State.SOURCE_CHANGING},\n\n // {name: Event.READY, from: State.SOURCE_CHANGING, to: State.READY},\n\n {name: Event.VIDEO_CHANGE, from: State.REBUFFERING, to: State.QUALITYCHANGE_REBUFFERING},\n {name: Event.AUDIO_CHANGE, from: State.REBUFFERING, to: State.QUALITYCHANGE_REBUFFERING},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE_REBUFFERING),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE_REBUFFERING),\n {name: 'FINISH_QUALITYCHANGE_REBUFFERING', from: State.QUALITYCHANGE_REBUFFERING, to: State.REBUFFERING},\n ],\n\n // Keep callbacks sorted by order in which they are called by JSM library (and after order, sorted by name)\n //\n // Do not use convenience, shortened callbacks\n // - instead of `onEVENT` use `onafterEVENT`\n // - instead of `onSTATE` use `onenterSTATE`\n //\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#callbacks\n callbacks: {\n onbeforeevent: (_event, from, to, _eventTimestamp: number, _eventData: AnalyticsEventBase): any => {\n if (from === State.REBUFFERING && to === State.QUALITYCHANGE_REBUFFERING) {\n // return false from an `onbeforeEVENT` handler to cancel the event.\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#callbacks\n //\n // Svarozic (2025-06-18):\n // Not sure if this works as expected because, according to DOCS (as far as I understand),\n // it should be in specific event callback `onbefore${EVENT_NAME}`\n return false;\n }\n },\n\n [`onleave${State.END_PLAY_SEEKING}`]: (\n _event,\n _from,\n to,\n eventTimestamp: number,\n eventData: AnalyticsEventBase,\n ) => {\n if (to === State.PLAY_SEEKING) {\n // seeking is not finished yet, do not send \"seeking\" sample\n return;\n }\n\n // seeking has finished / was interrupted - send out seeking sample\n const seekDuration = eventTimestamp - (this.seekStartTimestamp ?? eventTimestamp);\n this.seekStartTimestamp = undefined;\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventData);\n this.stateMachineCallbacks.end_play_seeking(seekDuration, 'end_play_seeking');\n },\n\n [`onleave${State.PLAYING}`]: () => {\n this.playingHeartbeatService.stopHeartbeat();\n },\n\n [`onleave${State.PLAY_SEEKING}`]: (_event, _from, to, eventTimestamp: number, _eventData) => {\n if (to === State.END_PLAY_SEEKING) {\n // regular seek workflow preparing to end seeking\n return;\n }\n\n // seek interrupted - not regular exit of seeking\n const seekDuration = eventTimestamp - (this.seekStartTimestamp ?? eventTimestamp);\n this.seekStartTimestamp = undefined;\n // we are using here state name `end_play_seeking` to not introduce another state to our database\n this.stateMachineCallbacks.end_play_seeking(seekDuration, 'end_play_seeking');\n },\n\n onleavestate: (event, from, to, eventTimestamp, eventData: AnalyticsEventBase) => {\n logStateMachineTransition('LEAVE', event, from, to);\n\n // Skip this JSM callback for JSM initial event\n // This event is fired when the state machine is constructed,\n // to transition us from 'none' to custom initial 'SETUP' state\n if (event === JSM_INITIAL_EVENT) {\n return;\n }\n\n if (from === State.REBUFFERING) {\n this.resetRebufferingHelpers();\n }\n\n // Skip this JSM callback when an JSM event without a timestamp is called,\n // because it would cause NPE in analytics code (state duration calculation etc.).\n // This probably has happened because the state machine was not used correctly,\n // aka. JSM event was not called via `callEvent` method as it should be!\n if (!eventTimestamp) {\n return;\n }\n\n this.addStatesToLog(event, from, to, eventTimestamp, eventData);\n const stateDuration = eventTimestamp - this.onEnterStateTimestamp;\n\n if (eventData && to !== State.END_PLAY_SEEKING) {\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventData);\n }\n\n if (eventData && event !== Event.END_AD) {\n this.lastTrackedVideoEndObject = eventData;\n }\n\n if ((from === State.READY || from === State.AD_STARTUP) && to === State.STARTUP) {\n this.setVideoStartTimeout();\n } else if (from === State.STARTUP && (to === State.PLAYING || to === State.AD_STARTUP)) {\n this.clearVideoStartTimeout();\n }\n\n const lowerCaseFrom = String(from).toLowerCase();\n if (to === State.VIDEOSTART_FAILED) {\n this.clearVideoStartTimeout();\n this.stateMachineCallbacks.videoStartFailed(stateDuration, createVideoStartFailedReason(event));\n } else if (from === State.END_PLAY_SEEKING) {\n // NOOP - skip last else block to not send sample\n // sending of sample is handled in `on Leave Seeking` state transition handler\n noOp();\n } else if (event === Event.UNLOAD) {\n this.stateMachineCallbacks.unload(stateDuration, lowerCaseFrom);\n } else if (\n from === State.AD_PAUSE ||\n from === State.AD_READY ||\n from === State.AD_PLAYING ||\n from === State.AD_STARTUP\n ) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(this.lastTrackedVideoEndObject);\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(this.lastTrackedVideoEndObject);\n this.stateMachineCallbacks.ad(stateDuration, 'ad');\n } else if (event === Event.START_AD && from === State.STARTUP) {\n noOp();\n } else if (event === Event.SOURCE_LOADED && from === State.INITIAL_SOURCE_CHANGE) {\n noOp();\n } else if (from === State.SETUP) {\n // Setting Player Startup Time to fixed value of 1ms.\n // We can not get correct Player Startup Time from bitmovin player, because it does not have an \"onInitialized\" event\n this.stateMachineCallbacks.setup(1, State.SETUP.toLowerCase());\n } else if (event === Event.PAUSE && from === State.STARTUP && to === State.READY) {\n // fired PAUSE event in STARTUP state indicates we are moving back to READY,\n // so we have to clean setTimeout, and we should not call any stateMachineCallbacks\n this.clearVideoStartTimeout();\n } else if (from !== State.ERROR) {\n // Default \"onleavestate\" state machine callback\n //\n // Every time, when we leave a state, we should try to call \"state\" callback,\n // to be able to make \"a cut\" and send analytics sample (if necessary)\n const defaultStateMachineCallbackFn = this.stateMachineCallbacks[lowerCaseFrom];\n if (typeof defaultStateMachineCallbackFn === 'function') {\n // a try-catch block to add more resilience against callback errors\n try {\n defaultStateMachineCallbackFn(stateDuration, lowerCaseFrom, eventData);\n } catch (e) {\n logger.error('Exception occurred in State Machine callback ' + lowerCaseFrom, eventData, e);\n }\n } else {\n // if callback is not defined, log a warning to indicate to the developer that\n // - a new callback function needs to be implemented to relay on this default state machine callback\n // - or if no callback is needed, we should\n // - early return from this JSM callback\n // - or add this state to the ignored list\n logMissingCallbackWarning(from, [State.READY, State.SOURCE_CHANGING]);\n }\n }\n\n if (\n eventData &&\n to !== State.END_PLAY_SEEKING &&\n from !== State.PLAY_SEEKING &&\n to !== State.PLAY_SEEKING &&\n from !== State.AD_STARTUP &&\n from !== State.AD_READY &&\n from !== State.AD_PLAYING &&\n from !== State.AD_PAUSE\n ) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventData);\n }\n\n if (event === Event.VIDEO_CHANGE) {\n this.stateMachineCallbacks.videoChange(eventData);\n } else if (event === Event.AUDIO_CHANGE) {\n this.stateMachineCallbacks.audioChange(eventData);\n } else if (event === Event.MUTE) {\n this.stateMachineCallbacks.mute();\n } else if (event === Event.UN_MUTE) {\n this.stateMachineCallbacks.unMute();\n }\n },\n\n [`onenter${State.PLAYING}`]: () => {\n this.playingHeartbeatService.startHeartbeat();\n },\n\n [`onenter${State.PLAY_SEEKING}`]: (event, from, _to, eventTimestamp: number, _eventData) => {\n if (from === State.END_PLAY_SEEKING) {\n // no start of seeking -> continues to seek and we don't need to have seek start timestamp\n return;\n }\n\n this.seekStartTimestamp = eventTimestamp;\n },\n\n onenterstate: (event, from, to, eventTimestamp: number, eventData: AnalyticsEventBase) => {\n logStateMachineTransition('ENTER', event, from, to);\n\n this.onEnterStateTimestamp = eventTimestamp ?? Date.now();\n // if customer set custom \"start time\" timestamp in AnalyticsStateMachineOptions of adapter constructor,\n // use it and override `onEnterStateTimestamp` during JSM initialization (transition to initial SETUP state)\n if (isNumber(opts.starttime) && event === JSM_INITIAL_EVENT) {\n this.onEnterStateTimestamp = opts.starttime;\n }\n\n if (\n eventData &&\n to !== State.END_PLAY_SEEKING &&\n from !== State.PLAY_SEEKING &&\n from !== State.AD_STARTUP &&\n from !== State.AD_READY &&\n from !== State.AD_PLAYING &&\n from !== State.AD_PAUSE &&\n !(event === Event.SEEK && from === State.END_PLAY_SEEKING)\n ) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventData);\n }\n\n if (event === Event.START_CAST && to === State.CASTING) {\n this.stateMachineCallbacks.startCasting(eventTimestamp, eventData);\n }\n\n if (to === State.REBUFFERING) {\n this.startRebufferingHeartbeatInterval();\n }\n },\n\n [`onafter${Event.ERROR}`]: (_event, _from, _to, _eventTimestamp, eventData: ErrorEvent) => {\n this.stateMachineCallbacks.error(eventData);\n },\n\n onafterevent: (event, from, to, eventTimestamp: number, eventData) => {\n if (event === Event.MANUAL_SOURCE_CHANGE && from === State.SETUP) {\n this.stateMachineCallbacks.initialSourceChange(eventData);\n } else if (event === Event.MANUAL_SOURCE_CHANGE) {\n this.stateMachineCallbacks.manualSourceChange(eventData);\n }\n\n if (to === State.QUALITYCHANGE_PAUSE) {\n this.stateMachine.FINISH_QUALITYCHANGE_PAUSE(eventTimestamp);\n }\n if (to === State.QUALITYCHANGE) {\n this.stateMachine.FINISH_QUALITYCHANGE(eventTimestamp);\n }\n if (to === State.QUALITYCHANGE_REBUFFERING) {\n this.stateMachine.FINISH_QUALITYCHANGE_REBUFFERING(eventTimestamp);\n }\n if (to === State.MUTING_READY || to === State.MUTING_PLAY || to === State.MUTING_PAUSE) {\n this.stateMachine.FINISH_MUTING(eventTimestamp);\n }\n },\n },\n });\n }\n\n override onSsaiPlaybackInteraction(timestamp: number, eventObject: AnalyticsEventBase) {\n // We don't allow this in any other state because it could interrupt the natural flow of the states\n // only PLAYING is considered a state which we can interrupt just like the heartbeat does\n // also we don't want to send samples with state we usually don't send samples like `ready`\n if (this.currentState != State.PLAYING) {\n return;\n }\n\n // Because ssai playback interaction can happen before Ssai Service is active (e.g. first ssai startAd call),\n // we need to manually mark sample as triggered by ssai\n //\n // This is also including the last sample marking, before a ssai ad block (due to ssai being spiky by design)\n this.sendPlayingSample(timestamp, eventObject, true);\n }\n\n getStates() {\n return this.debuggingStates;\n }\n\n setEnabledDebugging(enabled: boolean) {\n this.enabledDebugging = enabled;\n }\n\n private addStatesToLog(\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n timestamp: number,\n eventObject: any,\n ) {\n if (this.enabledDebugging) {\n this.debuggingStates.push(new EventDebugging(event, from, to, timestamp, eventObject));\n }\n }\n}\n","/*\n\n Javascript State Machine Library - https://github.com/jakesgordon/javascript-state-machine\n\n Copyright (c) 2012, 2013, 2014, 2015, Jake Gordon and contributors\n Released under the MIT license - https://github.com/jakesgordon/javascript-state-machine/blob/master/LICENSE\n\n*/\n\n(function () {\n\n var StateMachine = {\n\n //---------------------------------------------------------------------------\n\n VERSION: \"2.4.0\",\n\n //---------------------------------------------------------------------------\n\n Result: {\n SUCCEEDED: 1, // the event transitioned successfully from one state to another\n NOTRANSITION: 2, // the event was successfull but no state transition was necessary\n CANCELLED: 3, // the event was cancelled by the caller in a beforeEvent callback\n PENDING: 4 // the event is asynchronous and the caller is in control of when the transition occurs\n },\n\n Error: {\n INVALID_TRANSITION: 100, // caller tried to fire an event that was innapropriate in the current state\n PENDING_TRANSITION: 200, // caller tried to fire an event while an async transition was still pending\n INVALID_CALLBACK: 300 // caller provided callback function threw an exception\n },\n\n WILDCARD: '*',\n ASYNC: 'async',\n\n //---------------------------------------------------------------------------\n\n create: function(cfg, target) {\n\n var initial = (typeof cfg.initial == 'string') ? { state: cfg.initial } : cfg.initial; // allow for a simple string, or an object with { state: 'foo', event: 'setup', defer: true|false }\n var terminal = cfg.terminal || cfg['final'];\n var fsm = target || cfg.target || {};\n var events = cfg.events || [];\n var callbacks = cfg.callbacks || {};\n var map = {}; // track state transitions allowed for an event { event: { from: [ to ] } }\n var transitions = {}; // track events allowed from a state { state: [ event ] }\n\n var add = function(e) {\n var from = Array.isArray(e.from) ? e.from : (e.from ? [e.from] : [StateMachine.WILDCARD]); // allow 'wildcard' transition if 'from' is not specified\n map[e.name] = map[e.name] || {};\n for (var n = 0 ; n < from.length ; n++) {\n transitions[from[n]] = transitions[from[n]] || [];\n transitions[from[n]].push(e.name);\n\n map[e.name][from[n]] = e.to || from[n]; // allow no-op transition if 'to' is not specified\n }\n if (e.to)\n transitions[e.to] = transitions[e.to] || [];\n };\n\n if (initial) {\n initial.event = initial.event || 'startup';\n add({ name: initial.event, from: 'none', to: initial.state });\n }\n\n for(var n = 0 ; n < events.length ; n++)\n add(events[n]);\n\n for(var name in map) {\n if (map.hasOwnProperty(name))\n fsm[name] = StateMachine.buildEvent(name, map[name]);\n }\n\n for(var name in callbacks) {\n if (callbacks.hasOwnProperty(name))\n fsm[name] = callbacks[name]\n }\n\n fsm.current = 'none';\n fsm.is = function(state) { return Array.isArray(state) ? (state.indexOf(this.current) >= 0) : (this.current === state); };\n fsm.can = function(event) { return !this.transition && (map[event] !== undefined) && (map[event].hasOwnProperty(this.current) || map[event].hasOwnProperty(StateMachine.WILDCARD)); }\n fsm.cannot = function(event) { return !this.can(event); };\n fsm.transitions = function() { return (transitions[this.current] || []).concat(transitions[StateMachine.WILDCARD] || []); };\n fsm.isFinished = function() { return this.is(terminal); };\n fsm.error = cfg.error || function(name, from, to, args, error, msg, e) { throw e || msg; }; // default behavior when something unexpected happens is to throw an exception, but caller can override this behavior if desired (see github issue #3 and #17)\n fsm.states = function() { return Object.keys(transitions).sort() };\n\n if (initial && !initial.defer)\n fsm[initial.event]();\n\n return fsm;\n\n },\n\n //===========================================================================\n\n doCallback: function(fsm, func, name, from, to, args) {\n if (func) {\n try {\n return func.apply(fsm, [name, from, to].concat(args));\n }\n catch(e) {\n return fsm.error(name, from, to, args, StateMachine.Error.INVALID_CALLBACK, \"an exception occurred in a caller-provided callback function\", e);\n }\n }\n },\n\n beforeAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbeforeevent'], name, from, to, args); },\n afterAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafterevent'] || fsm['onevent'], name, from, to, args); },\n leaveAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleavestate'], name, from, to, args); },\n enterAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenterstate'] || fsm['onstate'], name, from, to, args); },\n changeState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onchangestate'], name, from, to, args); },\n\n beforeThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbefore' + name], name, from, to, args); },\n afterThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafter' + name] || fsm['on' + name], name, from, to, args); },\n leaveThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleave' + from], name, from, to, args); },\n enterThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenter' + to] || fsm['on' + to], name, from, to, args); },\n\n beforeEvent: function(fsm, name, from, to, args) {\n if ((false === StateMachine.beforeThisEvent(fsm, name, from, to, args)) ||\n (false === StateMachine.beforeAnyEvent( fsm, name, from, to, args)))\n return false;\n },\n\n afterEvent: function(fsm, name, from, to, args) {\n StateMachine.afterThisEvent(fsm, name, from, to, args);\n StateMachine.afterAnyEvent( fsm, name, from, to, args);\n },\n\n leaveState: function(fsm, name, from, to, args) {\n var specific = StateMachine.leaveThisState(fsm, name, from, to, args),\n general = StateMachine.leaveAnyState( fsm, name, from, to, args);\n if ((false === specific) || (false === general))\n return false;\n else if ((StateMachine.ASYNC === specific) || (StateMachine.ASYNC === general))\n return StateMachine.ASYNC;\n },\n\n enterState: function(fsm, name, from, to, args) {\n StateMachine.enterThisState(fsm, name, from, to, args);\n StateMachine.enterAnyState( fsm, name, from, to, args);\n },\n\n //===========================================================================\n\n buildEvent: function(name, map) {\n return function() {\n\n var from = this.current;\n var to = map[from] || (map[StateMachine.WILDCARD] != StateMachine.WILDCARD ? map[StateMachine.WILDCARD] : from) || from;\n var args = Array.prototype.slice.call(arguments); // turn arguments into pure array\n\n if (this.transition)\n return this.error(name, from, to, args, StateMachine.Error.PENDING_TRANSITION, \"event \" + name + \" inappropriate because previous transition did not complete\");\n\n if (this.cannot(name))\n return this.error(name, from, to, args, StateMachine.Error.INVALID_TRANSITION, \"event \" + name + \" inappropriate in current state \" + this.current);\n\n if (false === StateMachine.beforeEvent(this, name, from, to, args))\n return StateMachine.Result.CANCELLED;\n\n if (from === to) {\n StateMachine.afterEvent(this, name, from, to, args);\n return StateMachine.Result.NOTRANSITION;\n }\n\n // prepare a transition method for use EITHER lower down, or by caller if they want an async transition (indicated by an ASYNC return value from leaveState)\n var fsm = this;\n this.transition = function() {\n fsm.transition = null; // this method should only ever be called once\n fsm.current = to;\n StateMachine.enterState( fsm, name, from, to, args);\n StateMachine.changeState(fsm, name, from, to, args);\n StateMachine.afterEvent( fsm, name, from, to, args);\n return StateMachine.Result.SUCCEEDED;\n };\n this.transition.cancel = function() { // provide a way for caller to cancel async transition if desired (issue #22)\n fsm.transition = null;\n StateMachine.afterEvent(fsm, name, from, to, args);\n }\n\n var leave = StateMachine.leaveState(this, name, from, to, args);\n if (false === leave) {\n this.transition = null;\n return StateMachine.Result.CANCELLED;\n }\n else if (StateMachine.ASYNC === leave) {\n return StateMachine.Result.PENDING;\n }\n else {\n if (this.transition) // need to check in case user manually called transition() but forgot to return StateMachine.ASYNC\n return this.transition();\n }\n\n };\n }\n\n }; // StateMachine\n\n //===========================================================================\n\n //======\n // NODE\n //======\n if (typeof exports !== 'undefined') {\n if (typeof module !== 'undefined' && module.exports) {\n exports = module.exports = StateMachine;\n }\n exports.StateMachine = StateMachine;\n }\n //============\n // AMD/REQUIRE\n //============\n else if (typeof define === 'function' && define.amd) {\n define(function(require) { return StateMachine; });\n }\n //========\n // BROWSER\n //========\n else if (typeof window !== 'undefined') {\n window.StateMachine = StateMachine;\n }\n //===========\n // WEB WORKER\n //===========\n else if (typeof self !== 'undefined') {\n self.StateMachine = StateMachine;\n }\n\n}());\n","import {AnalyticsStateMachine} from '../../analyticsStateMachines/AnalyticsStateMachine';\nimport {EventDispatcher} from '../../core/EventDispatcher';\nimport QualityChangeService from '../../core/QualityChangeService';\nimport {SourceInfoFallbackService} from '../../core/SourceInfoFallbackService';\nimport {SsaiService} from '../../core/ssai/SsaiService';\nimport {Event, EventMap} from '../../enums/Event';\nimport {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {CustomDataValues} from '../../types/CustomDataValues';\nimport {DownloadSpeedInfo} from '../../types/DownloadSpeedInfo';\nimport {DrmPerformanceInfo} from '../../types/DrmPerformanceInfo';\nimport {NoExtraProperties} from '../../types/NoExtraProperties';\nimport {SegmentInfo} from '../../types/SegmentInfo';\nimport {defaultStateMachineCallbacks, StateMachineCallbacks} from '../../types/StateMachineCallbacks';\nimport {logger} from '../../utils/Logger';\nimport {getCurrentTimestamp} from '../../utils/Utils';\nimport {WindowEventTracker} from '../../utils/WindowEventTracker';\n\nimport {EventCallbackDispatcher} from './EventCallbackDispatcher';\n\n/**\n * Audio volume below this delta is considered zero.\n */\nconst volumeDelta = 0.01;\n\nexport abstract class InternalAdapter implements EventCallbackDispatcher {\n readonly stateMachineCallbacks: StateMachineCallbacks = {...defaultStateMachineCallbacks};\n readonly qualityChangeService: QualityChangeService = new QualityChangeService();\n readonly ssaiService = new SsaiService();\n\n protected stateMachine!: AnalyticsStateMachine;\n protected opts: AnalyticsStateMachineOptions;\n protected _onLicenseKeyReceived: EventDispatcher<{licenseKey: string}> = new EventDispatcher();\n protected _onLicenseCallFailed: EventDispatcher<any> = new EventDispatcher();\n\n protected sourceInfoFallbackService: SourceInfoFallbackService = new SourceInfoFallbackService();\n protected drmPerformanceInfo: DrmPerformanceInfo | undefined = undefined;\n protected abstract get currentTime(): number;\n\n private _windowEventTracker: WindowEventTracker = new WindowEventTracker();\n\n get windowEventTracker(): WindowEventTracker {\n return this._windowEventTracker;\n }\n\n get onLicenseKeyReceived() {\n return this._onLicenseKeyReceived;\n }\n\n get onLicenseCallFailed() {\n return this._onLicenseCallFailed;\n }\n\n get downloadSpeedInfo(): DownloadSpeedInfo {\n return {\n segmentsDownloadCount: 0,\n segmentsDownloadSize: 0,\n segmentsDownloadTime: 0,\n avgDownloadSpeed: 0,\n minDownloadSpeed: 0,\n maxDownloadSpeed: 0,\n avgTimeToFirstByte: 0,\n };\n }\n\n get segments(): SegmentInfo[] {\n return [];\n }\n\n constructor(opts?: AnalyticsStateMachineOptions) {\n if (!opts) {\n opts = {\n starttime: undefined,\n };\n }\n if (!opts.starttime) {\n opts.starttime = getCurrentTimestamp();\n }\n\n this.opts = opts;\n }\n\n release() {\n this.stateMachine.resetIntervals();\n this.stateMachineCallbacks.release();\n this.resetSourceRelatedState();\n this._windowEventTracker.release();\n }\n\n eventCallback = <StateMachineEvent extends keyof EventMap, StateMachineEventData extends EventMap[StateMachineEvent]>(\n event: StateMachineEvent,\n eventData: NoExtraProperties<EventMap[StateMachineEvent], StateMachineEventData>,\n ) => {\n eventData = eventData || {};\n if (!this.stateMachine) {\n logger.log(\"Bitmovin Analytics: StateMachine isn't ready yet\");\n } else {\n this.stateMachine.callEvent(event, eventData, Date.now());\n }\n };\n\n getCommonPlaybackInfo() {\n let scale = 1;\n if (window.devicePixelRatio > 0) {\n scale = window.devicePixelRatio;\n }\n\n return {\n screenHeight: window.screen.height * scale,\n screenWidth: window.screen.width * scale,\n };\n }\n\n clearValues(): void {\n // noop by default\n }\n\n clearSegments(): void {\n // noop by default\n }\n\n resetSourceRelatedState(): void {\n this.sourceInfoFallbackService.reset();\n this.drmPerformanceInfo = undefined;\n }\n\n setCustomData(values: CustomDataValues): void {\n const previousState = this.stateMachine.currentState;\n\n if (\n this.stateMachine.currentState &&\n (this.stateMachine.currentState === 'PAUSE' || this.stateMachine.currentState === 'PLAYING')\n ) {\n this.eventCallback(Event.CUSTOM_DATA_CHANGE, {\n currentTime: this.currentTime,\n });\n this.eventCallback(Event[previousState], {\n values,\n currentTime: this.currentTime,\n });\n } else {\n this.stateMachineCallbacks.customdatachange(undefined, undefined, {values});\n }\n }\n\n protected isAudioMuted(playerIsMuted: boolean, currentVolume: number): boolean {\n return playerIsMuted || currentVolume < volumeDelta;\n }\n}\n","import {AnalyticsEventBase} from '../types/EventData';\n\nexport const DEFAULT_HEARTBEAT_INTERVAL_MS = 59700;\n\nexport interface HeartbeatListener {\n onHeartbeat: (eventObject: AnalyticsEventBase) => void;\n}\n\nexport class HeartbeatService {\n private heartbeatInterval: number | undefined;\n private listener: HeartbeatListener | undefined;\n private readonly getPlayerCurrentTime: () => number;\n\n constructor(getPlayerCurrentTime: () => number) {\n this.getPlayerCurrentTime = getPlayerCurrentTime;\n }\n\n setListener(listener: HeartbeatListener) {\n this.listener = listener;\n }\n\n startHeartbeat() {\n if (this.heartbeatInterval !== undefined) {\n this.clearHeartbeat();\n }\n this.heartbeatInterval = window.setInterval(() => {\n const eventData: AnalyticsEventBase = {\n currentTime: this.getPlayerCurrentTime(),\n };\n this.listener?.onHeartbeat(eventData);\n }, DEFAULT_HEARTBEAT_INTERVAL_MS);\n }\n\n stopHeartbeat() {\n this.clearHeartbeat();\n }\n\n private clearHeartbeat() {\n window.clearTimeout(this.heartbeatInterval);\n this.heartbeatInterval = undefined;\n }\n}\n","export const generateUUID = (): string => {\n return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => {\n const r = (Math.random() * 16) | 0;\n const v = c === 'x' ? r : (r & 0x3) | 0x8;\n return v.toString(16);\n });\n};\n","import {DeferredLicenseLoadingAdapterAPI} from '../adapters/internal/DeferredLicenseLoadingAdapterAPI';\nimport {AnalyticsConfig, CollectorConfig} from '../types/AnalyticsConfig';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {LicensingRequest} from '../types/LicensingRequest';\nimport {LicenseCall} from '../utils/LicenseCall';\nimport {ANALYTICS_BACKEND_BASE_URL} from '../utils/Settings';\n\nimport {Backend} from './Backend';\nimport {DebuggingBackend} from './DebuggingBackend';\nimport {LicenseCheckingBackend} from './LicenseCheckingBackend';\nimport {LongPlaytimeFilteringBackend} from './LongPlaytimeFilteringBackend';\nimport {NoOpBackend} from './NoOpBackend';\nimport {SequenceNumberBackend} from './SequenceNumberBackend';\n\ninterface InternalCollectorConfig extends CollectorConfig {\n wrapBackend: (innerBackend: Backend) => Backend;\n}\n\nexport class BackendFactory {\n createBackend(\n analyticsConfig: AnalyticsConfig,\n licensingRequest: LicensingRequest,\n adapter: DeferredLicenseLoadingAdapterAPI,\n authenticationCallback: AuthenticationCallback,\n ): Backend {\n if (!this.isEnabled(analyticsConfig)) {\n return new NoOpBackend();\n }\n const inner = this.createInnerBackend(analyticsConfig, licensingRequest, adapter, authenticationCallback);\n return this.decorateWithDebuggingBackend(analyticsConfig, inner);\n }\n\n private decorateWithDebuggingBackend(config: AnalyticsConfig, backend: Backend): Backend {\n if (config.debug) {\n return new DebuggingBackend(config, backend);\n }\n return backend;\n }\n\n private decorateWithBackendFromConfigIfAvailable(analyticsConfig: AnalyticsConfig, innerBackend: Backend): Backend {\n if (\n analyticsConfig !== undefined &&\n analyticsConfig.config !== undefined &&\n (analyticsConfig.config as InternalCollectorConfig).wrapBackend !== undefined\n ) {\n return (analyticsConfig.config as InternalCollectorConfig).wrapBackend(innerBackend);\n }\n\n return innerBackend;\n }\n\n private isEnabled(analyticsConfig: AnalyticsConfig): boolean {\n return analyticsConfig.config === undefined || analyticsConfig.config.enabled !== false;\n }\n\n private createInnerBackend(\n analyticsConfig: AnalyticsConfig,\n licensingRequest: LicensingRequest,\n adapter: DeferredLicenseLoadingAdapterAPI,\n authenticationCallback: AuthenticationCallback,\n ): Backend {\n const backendUrl = (analyticsConfig.config && analyticsConfig.config.backendUrl) || ANALYTICS_BACKEND_BASE_URL;\n let innerBackend: Backend = new LicenseCheckingBackend(\n licensingRequest,\n LicenseCall,\n backendUrl,\n adapter,\n authenticationCallback,\n );\n innerBackend = this.decorateWithBackendFromConfigIfAvailable(analyticsConfig, innerBackend);\n\n const sequenceNumberAssigningBackend = new SequenceNumberBackend(innerBackend);\n return new LongPlaytimeFilteringBackend(sequenceNumberAssigningBackend);\n }\n}\n","export class Queue<T> {\n private readonly _items: T[] = [];\n\n get items(): ReadonlyArray<T> {\n return this._items;\n }\n\n get length() {\n return this._items.length;\n }\n\n offer(item: T) {\n this._items.push(item);\n }\n\n poll(): T | undefined {\n return this._items.shift();\n }\n\n clear() {\n this._items.splice(0);\n }\n\n limit(maxElements: number) {\n while (this._items.length > maxElements) {\n this.poll();\n }\n }\n}\n","import {PlayerSize} from '../enums/PlayerSize';\nimport {isNullish} from '../utils/Utils';\n\nexport interface PlaybackInfo {\n isLive?: boolean;\n playerTech?: string;\n videoDuration?: number;\n streamFormat?: string;\n progUrl?: string;\n m3u8Url?: string;\n mpdUrl?: string;\n videoWindowWidth?: number;\n videoWindowHeight?: number;\n isMuted?: boolean;\n videoBitrate?: number;\n audioBitrate?: number;\n droppedFrames: number;\n isCasting?: boolean;\n castTech?: string;\n screenHeight?: number;\n screenWidth?: number;\n videoPlaybackHeight?: number;\n videoPlaybackWidth?: number;\n videoTitle?: string;\n size?: PlayerSize;\n audioCodec?: string;\n videoCodec?: string;\n audioLanguage?: string;\n subtitleEnabled?: boolean;\n subtitleLanguage?: string;\n}\n\nexport function normalizeVideoDuration(playerVideoDuration: number | null | undefined): number {\n // This covers Live streams and any case in which the duration is not known\n // which should report 0 as videoDuration\n if (isNullish(playerVideoDuration) || Number.isNaN(playerVideoDuration) || playerVideoDuration === Infinity) {\n return 0;\n }\n return playerVideoDuration;\n}\n","export class ErrorCode {\n static BITMOVIN_PLAYER_LICENSING_ERROR = new ErrorCode(1103, '');\n static SETUP_MISSING_LICENSE_WHITELIST = new ErrorCode(1105, '');\n static QUALITY_CHANGE_THRESHOLD_EXCEEDED = new ErrorCode(10000, 'ANALYTICS_QUALITY_CHANGE_THRESHOLD_EXCEEDED');\n static BUFFERING_TIMEOUT_REACHED = new ErrorCode(10001, 'ANALYTICS_BUFFERING_TIMEOUT_REACHED');\n static VIDEO_STARTUP_TIMEOUT_REACHED = new ErrorCode(10002, 'ANALYTICS_VIDEOSTART_TIMEOUT_REACHED');\n\n private constructor(\n readonly code: number,\n readonly message: string,\n ) {}\n}\n","import {DeferredLicenseLoadingAdapterAPI} from '../adapters/internal/DeferredLicenseLoadingAdapterAPI';\nimport {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {LicenseCallFunc, LicensingRequest, LicensingResponse, LicensingResult} from '../types/LicensingRequest';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\nimport {ANALYTICS_LICENSECALL_TIMEOUT} from '../utils/Settings';\n\nimport {Backend} from './Backend';\nimport {NoOpBackend} from './NoOpBackend';\nimport {QueueBackend} from './QueueBackend';\nimport {RemoteBackend} from './RemoteBackend';\n\n/**\n * The `LicenseCheckingBackend` class is responsible for sending license requests\n * and routing samples to the appropriate backend based on the license status.\n *\n * The class manages a queue of samples during the license check process, ensuring that\n * samples are not lost while the license status is being determined. Once the license\n * is validated, the queued samples are flushed to the appropriate backend.\n *\n * @implements {Backend}\n */\nexport class LicenseCheckingBackend implements Backend {\n promise?: Promise<LicensingResponse>;\n private licenseLazyLoadingTimeoutHandle?: number;\n private backend: Backend;\n private info: LicensingRequest;\n\n constructor(\n info: LicensingRequest,\n private licenseCall: LicenseCallFunc,\n private backendBaseUrl: string,\n private adapter: DeferredLicenseLoadingAdapterAPI,\n private authenticationCallback: AuthenticationCallback,\n ) {\n this.info = {...info};\n this.backend = new QueueBackend();\n this.licenseCall = licenseCall;\n\n if (info.key !== undefined && info.key !== '') {\n this.promise = this.wrapLicenseCheckPromiseWithCallback(this.performLicenseCheck(), this.authenticationCallback);\n } else if (adapter.supportsDeferredLicenseLoading === true) {\n adapter.onLicenseKeyReceived.subscribe(this.licenseKeyReceived);\n adapter.onLicenseCallFailed.subscribe(this.licenseCallFailed);\n this.licenseLazyLoadingTimeoutHandle = window.setTimeout(\n this.licenseLazyLoadingTimeout,\n ANALYTICS_LICENSECALL_TIMEOUT,\n );\n } else {\n authenticationCallback.authenticationCompleted(false, undefined);\n this.backend = new NoOpBackend();\n }\n }\n\n performLicenseCheck(): Promise<LicensingResponse> {\n const {key, domain, version} = this.info;\n if (!key || key === '') {\n const error: LicensingResponse = {\n status: LicensingResult.Denied,\n message: 'No license key provided',\n };\n this.backend = new NoOpBackend();\n return Promise.resolve(error);\n }\n\n return this.licenseCall(key, domain, version, this.backendBaseUrl)\n .then((result) => {\n if (result.status === LicensingResult.Granted) {\n const remoteBackend = new RemoteBackend(true, this.backendBaseUrl, key);\n (this.backend as QueueBackend).flushTo(remoteBackend);\n this.backend = remoteBackend;\n } else {\n throw new Error(result.message);\n }\n return result;\n })\n .catch((err: Error) => {\n if (err.message === 'Ignoring Impression due to DNT Header being set') {\n logger.error('License Check for Bitmovin Analytics failed because of', err);\n } else {\n logger.errorMessageToUser('License Check for Bitmovin Analytics failed because of', err);\n }\n this.backend = new NoOpBackend();\n return {\n status: LicensingResult.Denied,\n message: err.message,\n };\n });\n }\n\n sendRequest(sample: Sample) {\n this.backend.sendRequest(sample);\n }\n sendUnloadRequest(sample: Sample) {\n this.backend.sendUnloadRequest(sample);\n }\n sendRequestSynchronous(sample: Sample) {\n this.backend.sendRequestSynchronous(sample);\n }\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.backend.sendAdRequest(sample);\n }\n\n private licenseKeyReceived = (eventArgs: {licenseKey: string}) => {\n clearTimeout(this.licenseLazyLoadingTimeoutHandle);\n this.unsubscribeFromAdapter();\n this.info.key = eventArgs.licenseKey;\n this.promise = this.wrapLicenseCheckPromiseWithCallback(this.performLicenseCheck(), this.authenticationCallback);\n };\n\n private licenseCallFailed = () => {\n clearTimeout(this.licenseLazyLoadingTimeoutHandle);\n this.unsubscribeFromAdapter();\n this.backend = new NoOpBackend();\n this.authenticationCallback.authenticationCompleted(false, undefined);\n };\n\n private licenseLazyLoadingTimeout = () => {\n this.unsubscribeFromAdapter();\n this.backend = new NoOpBackend();\n this.authenticationCallback.authenticationCompleted(false, undefined);\n };\n\n private unsubscribeFromAdapter() {\n this.adapter.onLicenseKeyReceived.unsubscribe(this.licenseKeyReceived);\n this.adapter.onLicenseCallFailed.unsubscribe(this.licenseCallFailed);\n }\n\n private wrapLicenseCheckPromiseWithCallback(\n promise: Promise<LicensingResponse>,\n authenticationCallback: AuthenticationCallback,\n ): Promise<LicensingResponse> {\n return promise.then((response) => {\n authenticationCallback.authenticationCompleted(response.status === LicensingResult.Granted, response.features);\n return response;\n });\n }\n}\n","import {Event} from './Event';\n\nexport enum VideoStartFailedReason {\n PAGE_CLOSED = 'PAGE_CLOSED',\n PLAYER_ERROR = 'PLAYER_ERROR',\n TIMEOUT = 'TIMEOUT',\n UNKNOWN = 'UNKNOWN',\n}\n\nexport function createVideoStartFailedReason(stateMachineEvent: string | undefined): VideoStartFailedReason {\n switch (stateMachineEvent) {\n case Event.ERROR:\n return VideoStartFailedReason.PLAYER_ERROR;\n case Event.UNLOAD:\n return VideoStartFailedReason.PAGE_CLOSED;\n case Event.VIDEOSTART_TIMEOUT:\n return VideoStartFailedReason.TIMEOUT;\n\n default:\n return VideoStartFailedReason.UNKNOWN;\n }\n}\n","/* eslint-disable perfectionist/sort-enums */\n\nexport enum AD_TYPE {\n NO_AD = 0,\n CSAI = 1,\n SSAI = 2,\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","import {logger} from './Logger';\nimport * as Utils from './Utils';\nimport {isNullish} from './Utils';\n\nexport class ViewportTracker {\n private onIntersectionChanged: () => void;\n private observer?: IntersectionObserver;\n private element: HTMLElement;\n private inViewport?: boolean = undefined;\n private threshold: number;\n private hidden: string | undefined;\n private visibilityChange?: string;\n\n constructor(element: HTMLElement, onIntersectionChanged: () => void, threshold = 1.0) {\n this.threshold = threshold;\n this.onIntersectionChanged = onIntersectionChanged;\n this.element = element;\n\n try {\n const options: IntersectionObserverInit = {\n root: null,\n rootMargin: '0px',\n threshold,\n };\n this.observer = new IntersectionObserver((entries, observer) => this.handleIntersect(entries, observer), options);\n this.observer.observe(element);\n } catch (_error) {\n logger.log(\"Couldn't create instance of IntersectionObserver. timeInViewport will always be reported as 100%.\");\n }\n\n this.hidden = Utils.getHiddenProp();\n if (this.hidden) {\n this.visibilityChange = this.hidden.replace('hidden', '') + 'visibilitychange';\n document.addEventListener(\n this.visibilityChange,\n (this.handleVisibilityChange = this.handleVisibilityChange.bind(this)),\n false,\n );\n }\n }\n\n isHidden() {\n return this.hidden && document[this.hidden];\n }\n\n isInViewport(): boolean {\n return !this.isHidden() && (isNullish(this.inViewport) ? true : this.inViewport);\n }\n\n dispose() {\n if (this.observer) {\n this.observer.unobserve(this.element);\n this.observer.disconnect();\n }\n if (this.visibilityChange) {\n document.removeEventListener(this.visibilityChange, this.handleVisibilityChange, false);\n }\n }\n\n private handleVisibilityChange() {\n this.onIntersectionChanged();\n }\n\n private handleIntersect(entries: IntersectionObserverEntry[], _observer: IntersectionObserver) {\n entries.forEach((i) => {\n if (i.target === this.element) {\n this.inViewport = !(i.intersectionRatio < this.threshold);\n }\n });\n this.onIntersectionChanged();\n }\n}\n","import {SpeedMeasurement} from '../types/SpeedMeasurement';\n\nexport class Measure implements SpeedMeasurement {\n private download: SpeedMeasurement;\n\n get speed(): number {\n return this.download.size / this.download.duration;\n }\n get duration(): number {\n return this.download.duration;\n }\n get size(): number {\n return this.download.size;\n }\n get timeToFirstByte(): number {\n return this.download.timeToFirstByte;\n }\n get timestamp(): Date {\n return this.download.timestamp;\n }\n\n get httpStatus(): number {\n return this.download.httpStatus;\n }\n\n constructor(download: SpeedMeasurement) {\n this.download = download;\n }\n}\n","import type {SsaiAdBreakMetadata} from '../../api/AdapterAPI';\nimport {isNotNullish} from '../../utils/Utils';\n\n/**\n * Utility function to sanitize the adPosition value in the SsaiAdBreakMetadata object passed to Bitmovin8Adapter.\n *\n * Needed, because we have introduced SSAI API in `Bitmovin8Adapter` in v2.39.0, without doing proper validation of\n * the passed adPosition value and customer started to use us with invalid values (having `-` in string in JavaScript).\n * Because we did not want to break the customer's implementation, we decided to sanitize the value to the correct one.\n *\n * @deprecated This function will be removed in v3\n */\nexport const sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition = <T = unknown>(anything: T): T => {\n const maybeSsaiAdBreakMetadata = anything as SsaiAdBreakMetadata;\n\n if (isNotNullish(maybeSsaiAdBreakMetadata?.adPosition)) {\n if ((maybeSsaiAdBreakMetadata.adPosition as string) === 'pre-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'preroll';\n } else if ((maybeSsaiAdBreakMetadata.adPosition as string) === 'mid-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'midroll';\n } else if ((maybeSsaiAdBreakMetadata?.adPosition as string) === 'post-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'postroll';\n }\n }\n\n return maybeSsaiAdBreakMetadata as T;\n};\n","import type {SsaiAdBreakMetadata, SsaiAdMetadata, SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\nimport {AD_TYPE} from '../../enums/AdType';\nimport {ErrorCode} from '../../enums/ErrorCode';\nimport {customDataValuesKeys} from '../../types/CustomDataValues';\nimport type {AnalyticsEventBase} from '../../types/EventData';\nimport type {Sample} from '../../types/Sample';\nimport {isNotNullish} from '../../utils/Utils';\nimport {generateUUID} from '../../utils/uuidUtils';\n\nimport type {InternalSsaiMetadata, SsaiEngagementInteractionData} from './ssaiEngagementInteractionData';\nimport {\n getCurrentMonotonicTimestampInMs,\n getMonotonicTimestampInMsSince,\n SSAI_RELATED_SAMPLE_MARKER,\n} from './ssaiUtils';\n\nexport type SsaiEventHandler = {\n getPlayerCurrentTime: () => number;\n reportEngagementInteraction: (data: SsaiEngagementInteractionData) => void;\n reportPlaybackInteraction: (timestamp: number, eventData: AnalyticsEventBase) => void;\n};\n\nenum SsaiState {\n AD_BREAK_STARTED,\n ACTIVE,\n IDLE,\n}\n\n// we start with -1, to be able to increment it before sending the first sample\n// this way the current adIndex is the one of the current playing ad\nconst INITIAL_AD_INDEX_VALUE = -1;\n\nexport class SsaiService {\n /** if `undefined` then service is not active and should not do anything, why: initially we activate it only for Bitmovin8 */\n private eventHandler: SsaiEventHandler | undefined = undefined;\n\n /** Index of the current ad in the whole session */\n private adIndex: number = INITIAL_AD_INDEX_VALUE;\n\n private state: SsaiState = SsaiState.IDLE;\n private isFirstSampleOfAd = false;\n /**\n * represents the current playing ad metadata\n * is `undefined` when no ad is playing (after endAdBreak)\n * or omitted by customer\n */\n private currentAdMetadata: InternalSsaiMetadata | undefined;\n\n /**\n * The impression id for the currently playing ad\n * is undefined when no ad is playing\n */\n private currentAdImpressionId: string | undefined;\n\n /** List of quartiles already sent for the current ad */\n private sentAdQuartiles: SsaiAdQuartile[] = [];\n\n /**\n * Flags whether an error was sent during an ad to avoid sending multiple errors for one ad,\n * which would skew e.g. the ad abandonment rate.\n */\n private errorSent: boolean = false;\n\n /**\n * The timestamp marking when the `adStart` method was called.\n * This timestamp is used to calculate the time difference between the `adStart` call\n * and subsequent `adQuartileFinished` or `sendAdEngagementErrorSample` calls.\n */\n private timestampOfAdStart: number | undefined;\n\n activate(eventHandler: SsaiEventHandler) {\n this.eventHandler = eventHandler;\n }\n\n adBreakStart(adBreakMetadata?: SsaiAdBreakMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state != SsaiState.IDLE) {\n return;\n }\n\n this.state = SsaiState.AD_BREAK_STARTED;\n this.currentAdMetadata = {\n ...adBreakMetadata,\n };\n }\n\n adStart(adMetadata?: SsaiAdMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state == SsaiState.IDLE) {\n return;\n }\n\n const timestamp = new Date().getTime();\n const playerCurrentTime = this.eventHandler.getPlayerCurrentTime();\n\n // report playback sample - will be saved in our playback related data lake\n // - with the first adStart call we need to close the current normal playback sample (no ssai ad information yet because SsaiState is not yet set to active)\n // - with all following adStart calls, we will deliver previous ssai ad information (SsaiState is already set to active)\n this.eventHandler.reportPlaybackInteraction(timestamp, {currentTime: playerCurrentTime});\n\n this.state = SsaiState.ACTIVE;\n // to include the adIndex in the next sample which will be the first sample of this started ad\n this.isFirstSampleOfAd = true;\n this.adIndex++;\n\n this.resetAdData();\n\n this.currentAdMetadata = {\n adPosition: this.currentAdMetadata?.adPosition,\n adId: adMetadata?.adId,\n adSystem: adMetadata?.adSystem,\n customData: adMetadata?.customData,\n };\n\n this.currentAdImpressionId = generateUUID();\n this.timestampOfAdStart = getCurrentMonotonicTimestampInMs();\n\n // report engagement sample - will be saved in our ad related data lake\n this.eventHandler.reportEngagementInteraction({\n type: 'started',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n });\n }\n\n adQuartileFinished(adQuartile: SsaiAdQuartile, adQuartileMetadata: SsaiAdQuartileMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not activated\n return;\n }\n\n if (this.state != SsaiState.ACTIVE) {\n return;\n }\n\n if (this.sentAdQuartiles.includes(adQuartile)) {\n //do nothing if adQuartile was already sent\n return;\n }\n\n this.eventHandler.reportEngagementInteraction({\n type: 'quartile',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId!,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n quartile: adQuartile,\n quartileMetadata: adQuartileMetadata,\n timeSinceAdStartedInMs: getMonotonicTimestampInMsSince(this.timestampOfAdStart),\n });\n this.sentAdQuartiles.push(adQuartile);\n }\n\n adBreakEnd() {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state == SsaiState.IDLE) {\n return;\n }\n\n if (this.state == SsaiState.ACTIVE) {\n const timestamp = new Date().getTime();\n const playerCurrentTime = this.eventHandler.getPlayerCurrentTime();\n this.eventHandler.reportPlaybackInteraction(timestamp, {currentTime: playerCurrentTime});\n }\n\n this.resetAdBreakData();\n }\n\n manipulate(sample: Sample): void {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state != SsaiState.ACTIVE) {\n return;\n }\n\n sample.ad = AD_TYPE.SSAI;\n sample.adId = this.currentAdMetadata?.adId;\n sample.adSystem = this.currentAdMetadata?.adSystem;\n sample.adPosition = this.currentAdMetadata?.adPosition;\n // we only mark the first sample of an ssai ad with the index in the playback/audience data (non ad table)\n // this allows us to count the number of ads\n if (this.isFirstSampleOfAd) {\n sample.adIndex = this.adIndex;\n this.isFirstSampleOfAd = false;\n }\n\n const customData = this.currentAdMetadata?.customData;\n if (isNotNullish(customData)) {\n customDataValuesKeys.forEach((key) => {\n if (customData[key]) {\n sample[key] = customData[key];\n }\n });\n }\n\n sample[SSAI_RELATED_SAMPLE_MARKER] = true; // mark it as ssai sample\n }\n\n sendAdEngagementErrorSample(errorCode: number, errorMessage: string) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state !== SsaiState.ACTIVE) {\n return;\n }\n\n // only send one error sample per ad\n if (this.errorSent) {\n return;\n }\n\n // This error code is related to the Analytics product and is non-fatal.\n // It is not triggered by the Player and does not interrupt or affect playback,\n // so there is no need to report an ad error sample.\n if (errorCode === ErrorCode.QUALITY_CHANGE_THRESHOLD_EXCEEDED.code) {\n return;\n }\n\n this.eventHandler.reportEngagementInteraction({\n type: 'error',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId!,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n errorCode,\n errorMessage,\n timeSinceAdStartedInMs: getMonotonicTimestampInMsSince(this.timestampOfAdStart),\n });\n this.errorSent = true;\n }\n\n resetSourceRelatedState() {\n this.resetAdBreakData();\n this.adIndex = INITIAL_AD_INDEX_VALUE;\n }\n\n private resetAdBreakData() {\n this.state = SsaiState.IDLE;\n this.isFirstSampleOfAd = false;\n delete this.currentAdMetadata;\n this.resetAdData();\n }\n\n private resetAdData() {\n delete this.currentAdMetadata?.customData;\n delete this.currentAdMetadata?.adId;\n delete this.currentAdMetadata?.adSystem;\n this.errorSent = false;\n this.currentAdImpressionId = undefined;\n this.sentAdQuartiles = [];\n this.timestampOfAdStart = undefined;\n }\n}\n\nfunction isActivated(eventHandler: SsaiEventHandler | undefined): eventHandler is SsaiEventHandler {\n return isNotNullish(eventHandler);\n}\n","import {InternalAdapterAPI} from '../adapters/internal/InternalAdapterAPI';\nimport {AD_TYPE} from '../enums/AdType';\nimport {ErrorCode} from '../enums/ErrorCode';\nimport {PlayerSize} from '../enums/PlayerSize';\nimport {VideoStartFailedReason} from '../enums/VideoStartFailedReason';\nimport {ErrorDetailTrackingSettingsProvider} from '../features/errordetails/ErrorDetailTracking';\nimport {OnErrorDetailEventObject} from '../features/errordetails/OnErrorDetailEventObject';\nimport {FeatureManager} from '../features/FeatureManager';\nimport type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {CustomDataValues, extractCustomDataFieldsOnly} from '../types/CustomDataValues';\nimport * as EventData from '../types/EventData';\nimport {FeatureConfigContainer} from '../types/FeatureConfigContainer';\nimport {PlaybackInfo} from '../types/PlaybackInfo';\nimport {Sample} from '../types/Sample';\nimport Timespan from '../types/Timespan';\nimport {\n getDeviceInformationFromAnalyticsConfig,\n getDomainFromAnalyticsConfig,\n guardAgainstDuplicatedUserId,\n guardConfigChangeAgainstMissingIsLive,\n guardConfigChangeAgainstMissingTitle,\n mergeAnalyticsConfig,\n} from '../utils/analyticsConfigUtils';\nimport {CodecHelper} from '../utils/CodecHelper';\nimport {logger} from '../utils/Logger';\nimport {isBlank, isValidString} from '../utils/stringUtils';\nimport * as Utils from '../utils/Utils';\nimport {isNotNullish, isNullish} from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\nimport {VERSION} from '../utils/Version';\nimport {getWebOSTVModelName, hasWindowWebOSApi} from '../utils/WebOSUtils';\n\nimport {AdAnalytics} from './AdAnalytics';\nimport {Backend} from './Backend';\nimport {BackendFactory} from './BackendFactory';\nimport {EventDispatcher, Subscribable} from './EventDispatcher';\nimport {NoOpBackend} from './NoOpBackend';\nimport {SessionPersistenceHandler} from './SessionPersistenceHandler';\nimport {\n isSsaiEngagementErrorData,\n isSsaiEngagementQuartileData,\n isSsaiEngagementStartedData,\n SsaiEngagementInteractionData,\n} from './ssai/ssaiEngagementInteractionData';\nimport {\n createErrorAdSample,\n createQuartileAdSample,\n createStartedAdSample,\n SSAI_RELATED_SAMPLE_MARKER,\n} from './ssai/ssaiUtils';\n\nexport class Analytics {\n get version(): string {\n return VERSION;\n }\n\n static version: string = VERSION;\n\n private readonly adAnalytics: AdAnalytics | undefined;\n\n pageLoadTime = 0;\n playerStartupTime = 0;\n videoStartupTime = 0;\n autoplay: boolean | undefined = undefined;\n sample: Sample;\n backend!: Backend;\n errorDetailTrackingSettingsProvider: ErrorDetailTrackingSettingsProvider;\n\n private config: AnalyticsConfig;\n private droppedSampleFrames = 0;\n private startupTime = 0;\n\n private authenticationCallback: AuthenticationCallback = {\n authenticationCompleted: (success: boolean, featureConfigs?: FeatureConfigContainer) => {\n this.featureManager.configureFeatures(success, featureConfigs);\n },\n };\n\n // used only in tests to inject mocks\n constructor(\n initialAnalyticsConfig: AnalyticsConfig,\n private readonly adapter: InternalAdapterAPI,\n private readonly backendFactory: BackendFactory,\n private readonly sessionHandler: SessionPersistenceHandler,\n private readonly featureManager: FeatureManager<FeatureConfigContainer>,\n private readonly onErrorDetailEventDispatcher: EventDispatcher<OnErrorDetailEventObject>,\n ) {\n this.config = initialAnalyticsConfig;\n this.sessionHandler = new SessionPersistenceHandler(this.config);\n\n // eslint-disable-next-line @typescript-eslint/no-this-alias\n const that = this;\n this.errorDetailTrackingSettingsProvider = {\n get domain() {\n return getDomainFromAnalyticsConfig(that.config);\n },\n get licenseKey() {\n return that.config.key ?? '';\n },\n get impressionId() {\n return that.getCurrentImpressionId() ?? '';\n },\n get collectorConfig() {\n return that.config.config;\n },\n };\n\n const licenseKeyReceivedUnsubscriber = this.adapter.onLicenseKeyReceived.subscribe(\n (eventArgs: {licenseKey: string}) => {\n if (!this.config.key) {\n this.config.key = eventArgs.licenseKey;\n }\n licenseKeyReceivedUnsubscriber();\n },\n );\n\n this.sample = this.setupSample();\n this.init();\n this.setupStateMachineCallbacks();\n const features = this.adapter.initialize(this);\n this.featureManager.registerFeatures(features);\n\n if (this.adapter.adModule) {\n this.adAnalytics = new AdAnalytics(this, this.adapter.adModule);\n }\n }\n\n get errorDetailSubscribable(): Subscribable<OnErrorDetailEventObject> {\n return this.onErrorDetailEventDispatcher;\n }\n\n getPlayerInformationFromAdapter() {\n const player = this.config.player || this.adapter.getPlayerName();\n return {\n player,\n version: player + '-' + this.adapter.getPlayerVersion(),\n playerTech: this.adapter.getPlayerTech(),\n };\n }\n\n init() {\n if (\n this.adapter.supportsDeferredLicenseLoading !== true &&\n (!isValidString(this.config.key) || isBlank(this.config.key))\n ) {\n logger.errorMessageToUser('Invalid analytics license key provided');\n return;\n }\n\n logger.initialize(this.config.debug);\n\n this.featureManager.resetFeatures();\n this.backend = this.createBackend(this.config);\n this.videoStartupTime = 0;\n\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n\n this.generateNewImpressionId();\n this.setUserId();\n\n if (this.adapter.videoCompletionTracker) {\n this.adapter.videoCompletionTracker.reset();\n }\n\n this.adapter.qualityChangeService.resetValues();\n this.adapter.ssaiService.resetSourceRelatedState();\n }\n\n release() {\n this.backend = new NoOpBackend();\n this.adAnalytics?.release();\n this.adapter.qualityChangeService.stopResetInterval();\n }\n\n setConfigParameters() {\n this.sample.key = this.config.key;\n this.sample.playerKey = this.config.playerKey;\n if (this.config.player) {\n this.sample.player = this.config.player;\n }\n this.sample.domain = getDomainFromAnalyticsConfig(this.config);\n\n this.sample.deviceInformation = getDeviceInformationFromAnalyticsConfig(this.config);\n\n this.sample.cdnProvider = this.config.cdnProvider;\n this.sample.videoId = this.config.videoId;\n this.sample.videoTitle = this.config.title;\n this.sample.customUserId = this.config.userId ?? this.config.customUserId;\n\n Utils.transferCustomDataFields(this.config, this.sample);\n\n this.sample.experimentName = this.config.experimentName;\n }\n\n generateNewImpressionId() {\n this.sample.impressionId = generateUUID();\n }\n\n setUserId() {\n this.sample.userId = this.sessionHandler.userId;\n }\n\n setAutoDetectedDeviceInformation(): void {\n // do not overwrite existing model value (set through config)\n if (isNotNullish(this.sample.deviceInformation?.model)) {\n return;\n }\n\n if (!hasWindowWebOSApi()) return;\n\n const modelName = getWebOSTVModelName();\n if (isNullish(modelName)) return;\n\n this.sample.deviceInformation = this.sample.deviceInformation ?? {};\n this.sample.deviceInformation.model = modelName;\n }\n\n private setupStateMachineCallbacks() {\n // All of these are called in the onLeaveState Method.\n // So it's the last sample\n this.adapter.stateMachineCallbacks.setup = (duration: number, state: string) => {\n logger.log(\n 'Setup bitmovin analytics ' + this.sample.analyticsVersion + ' with impressionId: ' + this.sample.impressionId,\n );\n\n this.setDuration(duration);\n this.setState(state);\n this.playerStartupTime = this.sample.playerStartupTime = duration;\n\n if (window.performance && window.performance.timing) {\n const loadTime = Utils.getCurrentTimestamp() - window.performance.timing.navigationStart;\n this.pageLoadTime = this.sample.pageLoadTime = loadTime;\n }\n\n this.startupTime = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n\n this.sample.pageLoadTime = 0;\n };\n\n this.adapter.stateMachineCallbacks.startup = (duration: number, state: string) => {\n this.sample.supportedVideoCodecs = CodecHelper.supportedVideoFormats;\n this.setState(state);\n\n // videoStartupTime has to be > 0 on startup sample\n // it is used to mark a successfull impression and billing depends on it\n const sanitizedStartupDuration = Math.max(duration, 1);\n\n const startupTimeSum = (this.startupTime || 0) + sanitizedStartupDuration;\n this.sample.startupTime = startupTimeSum;\n this.startupTime = startupTimeSum;\n\n this.setDuration(sanitizedStartupDuration);\n this.videoStartupTime = sanitizedStartupDuration;\n this.sample.videoStartupTime = sanitizedStartupDuration;\n\n this.autoplay = this.sample.autoplay = this.adapter.getAutoPlay();\n this.adapter.qualityChangeService.setStartupHasFinished();\n\n const drmPerformance = this.adapter.getDrmPerformanceInfo();\n if (isNotNullish(drmPerformance)) {\n this.sample.drmType = drmPerformance.drmType;\n this.sample.drmLoadTime = drmPerformance.drmLoadTime;\n }\n\n this.sendAnalyticsRequestAndClearValues();\n this.sample.autoplay = undefined;\n };\n\n this.adapter.stateMachineCallbacks.playing = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.played = duration;\n this.setCompletionValues();\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.unload = (duration: number, state: string) => {\n let videoStartForClosedState = this.sample.videoTimeStart;\n if (state === 'playing') {\n this.setDuration(duration);\n this.setState(state);\n this.sample.played = duration;\n this.setCompletionValues();\n this.sendUnloadRequest();\n if (Utils.isNumber(this.sample.videoTimeEnd)) {\n videoStartForClosedState = this.sample.videoTimeEnd;\n }\n }\n\n if (this.videoStartupTime > 0) {\n this.setVideoTimeStart(videoStartForClosedState);\n this.setVideoTimeEnd(videoStartForClosedState);\n this.clearValues();\n this.setState('closed');\n this.sendUnloadRequest();\n }\n };\n\n this.adapter.stateMachineCallbacks.heartbeat = (duration, state, heartbeatPayload) => {\n this.setState(state);\n this.setDuration(duration);\n\n this.sample = {\n ...this.sample,\n ...heartbeatPayload,\n };\n\n if (state === 'playing') {\n this.setCompletionValues();\n }\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.qualitychange = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.qualitychange_pause = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.qualitychange_rebuffering = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.videoChange = (event: any) => {\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n this.setPlaybackVideoPropertiesFromEvent(event);\n };\n\n this.adapter.stateMachineCallbacks.audioChange = (event: any) => {\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n this.setPlaybackAudioPropertiesFromEvent(event);\n };\n\n this.adapter.stateMachineCallbacks.audiotrack_changing = () => {\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.pause = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n\n this.sample.paused = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n /** @deprecated this function was created only to unify the sample sending for seeking, until deprecated callbacks are removed. */\n const sendSeekingSample = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.seeked = duration;\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.seeking = (duration: number) => sendSeekingSample(duration, 'seeking');\n this.adapter.stateMachineCallbacks.paused_seeking = sendSeekingSample;\n this.adapter.stateMachineCallbacks.end_play_seeking = sendSeekingSample;\n\n this.adapter.stateMachineCallbacks.rebuffering = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n\n this.sample.buffered = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.videoStartFailed = (duration, reason) => {\n this.setState('startup');\n this.sample.videoStartFailed = true;\n this.sample.videoStartFailedReason = reason;\n this.sample.duration = duration;\n\n if (reason === VideoStartFailedReason.PLAYER_ERROR) {\n // on player error we should not send a video startup sample\n return;\n }\n\n if (reason === VideoStartFailedReason.TIMEOUT) {\n this.sample.errorCode = ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED.code;\n this.sample.errorMessage = ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED.message;\n\n this.onErrorDetailEventDispatcher.dispatch({\n ...ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED,\n });\n }\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.error = (event: Readonly<EventData.ErrorEvent>) => {\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n\n this.setState('error');\n this.sample.errorCode = event.code;\n this.sample.errorMessage = event.message;\n this.sample.errorData = JSON.stringify(event.legacyData);\n this.sample.errorSegments = this.adapter.segments.map((s) => s.name);\n\n if (this.adapter.onError) {\n this.adapter.onError();\n }\n\n this.onErrorDetailEventDispatcher.dispatch({\n code: event.code,\n message: event.message,\n errorData: event.data,\n });\n\n this.sendAnalyticsRequestAndClearValues();\n\n delete this.sample.errorCode;\n delete this.sample.errorMessage;\n delete this.sample.errorData;\n };\n\n this.adapter.stateMachineCallbacks.ad = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.ad = AD_TYPE.CSAI;\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.mute = () => {\n this.sample.isMuted = true;\n };\n\n this.adapter.stateMachineCallbacks.unMute = () => {\n this.sample.isMuted = false;\n };\n\n this.adapter.stateMachineCallbacks.subtitle_changing = () => {\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent = (event: any) => {\n if (Utils.isNumber(event.currentTime)) {\n this.setVideoTimeEnd(Utils.calculateTime(event.currentTime));\n }\n };\n\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent = (event: any) => {\n if (Utils.isNumber(event.currentTime)) {\n this.setVideoTimeStart(Utils.calculateTime(event.currentTime));\n }\n };\n\n this.adapter.stateMachineCallbacks.manualSourceChange = (event: {config: AnalyticsConfig}) => {\n this.adapter.resetSourceRelatedState();\n this.sample = this.setupSample();\n this.startupTime = 0;\n this.config = Object.keys(event.config).length > 0 ? event.config : this.config;\n this.init();\n };\n\n this.adapter.stateMachineCallbacks.playlistTransition = (_event: EventData.AnalyticsEventBase) => {\n this.sample = this.setupSample();\n this.startupTime = 0;\n // init is needed because of resetting sequence number which\n // is done inside SequenceNumberBackend\n this.init();\n };\n\n this.adapter.stateMachineCallbacks.initialSourceChange = (event: {config: AnalyticsConfig}) => {\n this.config = event.config;\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n // The video has ended and we set up for a new impression\n this.adapter.stateMachineCallbacks.end = () => {\n this.sample = this.setupSample();\n this.startupTime = 0;\n this.init();\n };\n\n this.adapter.stateMachineCallbacks.release = () => {\n this.release();\n };\n\n this.adapter.stateMachineCallbacks.customdatachange = (\n _duration?: number,\n _state?: string,\n event?: {values: CustomDataValues},\n ) => {\n if (event && event.values) {\n this.changeCustomData(event.values);\n }\n };\n }\n\n sourceChange = (config: AnalyticsConfig | null | undefined) => {\n logger.log('Processing Source Change for Analytics', config);\n if (isNullish(config)) {\n this.adapter.sourceChange(this.config);\n return;\n }\n\n guardConfigChangeAgainstMissingTitle(this.config, config);\n guardConfigChangeAgainstMissingIsLive(this.config, config);\n guardAgainstDuplicatedUserId(config);\n\n const newConfig = mergeAnalyticsConfig(this.config, config);\n this.adapter.sourceChange(newConfig);\n };\n\n setCustomDataOnce = (values: CustomDataValues) => {\n const oldConfig = {...this.config};\n this.setState('customdatachange');\n this.sendAnalyticsRequestAndClearValues(values);\n // this method doesn't call changeCustomData() second time because in that method we have check for null values\n // to prevent overriding existing customData values with null if some field in object doesn't have value\n // because of that if some customData field had previous value null and it got changed to something else\n // it will not be possible to return it back to null using that method\n this.config = {...oldConfig};\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n setCustomData = (values: CustomDataValues) => {\n this.adapter.setCustomData(values);\n };\n\n getCurrentImpressionId = (): string | undefined => {\n return this.sample.impressionId;\n };\n\n getUserId = (): string => {\n return this.sessionHandler.userId;\n };\n\n setDuration(duration: number) {\n this.sample.duration = duration;\n }\n\n setState(state: string) {\n this.sample.state = state;\n }\n\n setPlaybackVideoPropertiesFromEvent(event: any) {\n if (Utils.isNumber(event.width)) {\n this.sample.videoPlaybackWidth = event.width;\n }\n if (Utils.isNumber(event.height)) {\n this.sample.videoPlaybackHeight = event.height;\n }\n if (Utils.isNumber(event.bitrate)) {\n this.sample.videoBitrate = event.bitrate;\n }\n if (isValidString(event.codec)) {\n this.sample.videoCodec = event.codec;\n }\n }\n\n setPlaybackAudioPropertiesFromEvent(event: any) {\n if (Utils.isNumber(event.bitrate)) {\n this.sample.audioBitrate = event.bitrate;\n }\n if (isValidString(event.codec)) {\n this.sample.audioCodec = event.codec;\n }\n }\n\n setPlaybackInfoFromAdapter() {\n const info = this.adapter.getCurrentPlaybackInfo();\n if (!info) {\n return;\n }\n\n // if set, we always apply `config.isLive` in favor of `info.isLive`\n this.sample.isLive = isNotNullish(this.config.isLive) ? this.config.isLive : info.isLive;\n // if `isLive` is still not defined, we set it to default `false` value\n if (isNullish(this.sample.isLive)) {\n this.sample.isLive = false;\n }\n\n if (isValidString(info.size)) {\n this.sample.size = info.size;\n }\n if (isValidString(info.playerTech)) {\n this.sample.playerTech = info.playerTech;\n }\n if (Utils.isNumber(info.videoDuration)) {\n this.sample.videoDuration = Utils.calculateTime(info.videoDuration || 0);\n }\n if (isValidString(info.streamFormat)) {\n this.sample.streamFormat = info.streamFormat;\n }\n if (isValidString(info.mpdUrl)) {\n this.sample.mpdUrl = info.mpdUrl;\n }\n if (isValidString(info.m3u8Url)) {\n this.sample.m3u8Url = info.m3u8Url;\n }\n if (isValidString(info.progUrl)) {\n this.sample.progUrl = info.progUrl;\n }\n if (Utils.isNumber(info.videoWindowWidth)) {\n this.sample.videoWindowWidth = info.videoWindowWidth;\n }\n if (Utils.isNumber(info.videoWindowHeight)) {\n this.sample.videoWindowHeight = info.videoWindowHeight;\n }\n if (Utils.isNumber(info.screenHeight)) {\n this.sample.screenHeight = info.screenHeight;\n }\n if (Utils.isNumber(info.screenWidth)) {\n this.sample.screenWidth = info.screenWidth;\n }\n if (Utils.isBoolean(info.isMuted)) {\n this.sample.isMuted = info.isMuted;\n }\n if (Utils.isBoolean(info.isCasting)) {\n this.sample.isCasting = info.isCasting;\n }\n if (isValidString(info.castTech)) {\n this.sample.castTech = info.castTech;\n }\n if (isValidString(info.videoTitle) && !this.config.title) {\n this.sample.videoTitle = info.videoTitle;\n }\n if (isValidString(info.audioCodec)) {\n this.sample.audioCodec = info.audioCodec;\n }\n if (isValidString(info.videoCodec)) {\n this.sample.videoCodec = info.videoCodec;\n }\n if (isValidString(info.audioLanguage)) {\n this.sample.audioLanguage = info.audioLanguage;\n }\n if (Utils.isBoolean(info.subtitleEnabled)) {\n this.sample.subtitleEnabled = info.subtitleEnabled;\n }\n if (isValidString(info.subtitleLanguage)) {\n this.sample.subtitleLanguage = info.subtitleLanguage;\n } else {\n this.sample.subtitleLanguage = undefined;\n }\n if (Utils.isNumber(info.droppedFrames)) {\n this.sample.droppedFrames = Math.max(info.droppedFrames - this.droppedSampleFrames, 0);\n this.droppedSampleFrames = info.droppedFrames;\n }\n }\n\n setupSample(): Sample {\n this.droppedSampleFrames = 0;\n\n return {\n platform: 'web',\n playerStartupTime: 0,\n pageLoadType: Utils.getPageLoadType(),\n path: Utils.sanitizePath(window.location.pathname),\n language: navigator.language || (navigator as any).userLanguage,\n userAgent: navigator.userAgent,\n screenWidth: screen.width,\n screenHeight: screen.height,\n isLive: this.config.isLive ?? false,\n videoDuration: 0,\n size: PlayerSize.Window,\n time: 0,\n videoWindowWidth: 0,\n videoWindowHeight: 0,\n droppedFrames: 0,\n played: 0,\n buffered: 0,\n paused: 0,\n ad: 0,\n seeked: 0,\n videoPlaybackWidth: 0,\n videoPlaybackHeight: 0,\n videoBitrate: 0,\n audioBitrate: 0,\n videoTimeStart: 0,\n videoTimeEnd: 0,\n videoStartupTime: 0,\n duration: 0,\n startupTime: 0,\n analyticsVersion: VERSION,\n pageLoadTime: 0,\n completedTotal: 0,\n ...this.getPlayerInformationFromAdapter(),\n };\n }\n\n sendAnalyticsRequest(customDataOnceValues?: CustomDataValues) {\n this.setPlaybackInfoFromAdapter();\n this.sample.time = Utils.getCurrentTimestamp();\n this.sample.downloadSpeedInfo = this.adapter.downloadSpeedInfo;\n\n this.adapter.ssaiService.manipulate(this.sample);\n\n // if we have received custom data from the setCustomDataOnce API call, we need to set\n // them as \"the last one\" (we need to override normal customData and SSAI custom data)\n if (customDataOnceValues != null) {\n this.changeCustomData(customDataOnceValues);\n }\n\n // Initial quality info should be available for the first sample after setup, so if there is no quality info yet, we try to set it *before* sending a sample.\n // In the general case, a qualitychange event first triggers a sample of the state we were in before the qualitychange sample itself is sent.\n // So to only report quality updates on the qualitychange sample and not the ones before it, we need to update the quality info *after* sending a sample,\n // making it available for future samples (e.g. qualitychange sample).\n // We only check videoBitrate and not audioBitrate since the latter is often reported as null/0 anyways.\n if (isNullish(this.sample.videoBitrate) || this.sample.videoBitrate <= 0) {\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n const copySample = {...this.sample};\n this.backend.sendRequest(copySample);\n } else {\n const copySample = {...this.sample};\n this.backend.sendRequest(copySample);\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n }\n }\n\n sendAnalyticsRequestAndClearValues(customDataOnceValues?: CustomDataValues) {\n this.sendAnalyticsRequest(customDataOnceValues);\n this.clearValues();\n }\n\n sendSsaiEngagementAdSample(data: SsaiEngagementInteractionData) {\n if (this.config.config?.ssaiEngagementTrackingEnabled !== true) {\n // if not enabled in config, do not send SSAI engagement AdSample\n return;\n }\n\n if (isSsaiEngagementStartedData(data)) {\n const ssaiAdSample = createStartedAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiAdSample);\n return;\n }\n\n if (isSsaiEngagementQuartileData(data)) {\n const ssaiAdSample = createQuartileAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiAdSample);\n return;\n }\n\n if (isSsaiEngagementErrorData(data)) {\n const ssaiErrorAdSample = createErrorAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiErrorAdSample);\n return;\n }\n }\n\n sendUnloadRequest() {\n this.backend.sendUnloadRequest(this.sample);\n }\n\n clearValues() {\n this.sample.ad = 0;\n this.sample.paused = 0;\n this.sample.played = 0;\n this.sample.seeked = 0;\n this.sample.buffered = 0;\n\n this.sample.playerStartupTime = 0;\n this.sample.videoStartupTime = 0;\n this.sample.startupTime = 0;\n this.sample.castTech = undefined;\n\n this.sample.duration = 0;\n this.sample.droppedFrames = 0;\n\n this.sample.drmLoadTime = undefined;\n\n this.sample.videoStartFailed = undefined;\n this.sample.videoStartFailedReason = undefined;\n\n this.sample.completed = undefined;\n\n this.sample.adId = undefined;\n this.sample.adSystem = undefined;\n this.sample.adPosition = undefined;\n this.sample.adIndex = undefined;\n\n this.sample[SSAI_RELATED_SAMPLE_MARKER] = undefined;\n\n this.adapter.clearValues();\n }\n\n /**\n * This method sanitizes the input and updates the analytics config.\n * @param values Object containing the customData and other fields\n */\n private changeCustomData = (values: CustomDataValues) => {\n this.config = {\n ...this.config,\n ...extractCustomDataFieldsOnly(values),\n };\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n private createBackend(config: AnalyticsConfig): Backend {\n const domain = getDomainFromAnalyticsConfig(config);\n return this.backendFactory.createBackend(\n config,\n {key: config.key, domain, version: VERSION},\n this.adapter,\n this.authenticationCallback,\n );\n }\n\n private setCompletionValues() {\n if (this.adapter.videoCompletionTracker) {\n const completed = this.adapter.videoCompletionTracker.addWatched({\n start: this.sample.videoTimeStart,\n end: this.sample.videoTimeEnd,\n } as Timespan);\n const completedTotal = this.adapter.videoCompletionTracker.getCompletionPercentage();\n\n if (!Number.isNaN(completed) && !Number.isNaN(completedTotal)) {\n this.sample.completed = completed;\n this.sample.completedTotal = completedTotal;\n }\n }\n }\n\n private setVideoTimeStart(value: number | undefined) {\n this.sample.videoTimeStart = value;\n }\n\n private setVideoTimeEnd(value: number | undefined) {\n this.sample.videoTimeEnd = value;\n }\n\n private sendQualityChange(state: string, duration: number): void {\n this.adapter.qualityChangeService.startResetInterval();\n\n this.adapter.qualityChangeService.increaseCounter();\n if (!this.adapter.qualityChangeService.isQualityChangeEventEnabled()) {\n this.setDuration(duration);\n this.adapter.stateMachineCallbacks.error({\n ...ErrorCode.QUALITY_CHANGE_THRESHOLD_EXCEEDED,\n legacyData: undefined,\n currentTime: undefined,\n data: {\n /*TODO additionalData: 'Add description for this error'*/\n },\n });\n } else {\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n this.setDuration(duration);\n this.setState(state);\n this.sendAnalyticsRequestAndClearValues();\n }\n }\n\n static create(config: AnalyticsConfig, adapter: InternalAdapterAPI): Analytics {\n const backendFactory: BackendFactory = new BackendFactory();\n const sessionHandler: SessionPersistenceHandler = new SessionPersistenceHandler(config);\n const featureManager = new FeatureManager<FeatureConfigContainer>();\n const onErrorDetailEventDispatcher = new EventDispatcher<OnErrorDetailEventObject>();\n return new Analytics(config, adapter, backendFactory, sessionHandler, featureManager, onErrorDetailEventDispatcher);\n }\n}\n\n// We separate the quality info from `setPlaybackInfoFromAdapter` to be able to explicitly set/update the quality info only when it changes.\nexport function setQualityInfoOnSample(sample: Sample, playbackInfo: PlaybackInfo) {\n if (Utils.isNumber(playbackInfo.videoPlaybackHeight)) {\n sample.videoPlaybackHeight = playbackInfo.videoPlaybackHeight;\n }\n if (Utils.isNumber(playbackInfo.videoPlaybackWidth)) {\n sample.videoPlaybackWidth = playbackInfo.videoPlaybackWidth;\n }\n if (Utils.isNumber(playbackInfo.videoBitrate)) {\n sample.videoBitrate = playbackInfo.videoBitrate;\n }\n if (Utils.isNumber(playbackInfo.audioBitrate)) {\n sample.audioBitrate = playbackInfo.audioBitrate;\n }\n}\n","export enum CdnProvider {\n AKAMAI = 'akamai',\n BITGRAVITY = 'bitgravity',\n CHINACACHE = 'chinacache',\n CLOUDFLARE = 'cloudflare',\n CLOUDFRONT = 'cloudfront',\n FASTLY = 'fastly',\n MAXCDN = 'maxcdn',\n}\n","/*!\n * This file was created to only avoid \"values imports\" (constants/enums/classes/etc.) from the `bitmovin-player@8.220.0`\n * to avoid including the whole package in our distribution code.\n *\n * We should still use \"type imports\" (`import type {}`) from the library!\n *\n * Unit test should cover \"copies of the library values\" to be sure they are up to date with the library!\n */\n\n/* eslint-disable perfectionist/sort-enums */\n\n/**\n * Copy of `HttpRequestType` enum from Bitmovin Player\n *\n * @see https://github.com/bitmovin-engineering/bitdash/blob/v8.220.0/src/core/NetworkAPI.ts#L11\n */\nexport enum HttpRequestType {\n MANIFEST_DASH = 'manifest/dash',\n MANIFEST_HLS_MASTER = 'manifest/hls/master',\n MANIFEST_HLS_VARIANT = 'manifest/hls/variant',\n MANIFEST_SMOOTH = 'manifest/smooth',\n MANIFEST_ADS = 'manifest/ads',\n\n MEDIA_AUDIO = 'media/audio',\n MEDIA_VIDEO = 'media/video',\n MEDIA_SUBTITLES = 'media/subtitles',\n MEDIA_THUMBNAILS = 'media/thumbnails',\n MEDIA_SEGMENTINDEX = 'media/segmentindex',\n\n DRM_LICENSE_WIDEVINE = 'drm/license/widevine',\n DRM_LICENSE_PLAYREADY = 'drm/license/playready',\n DRM_LICENSE_FAIRPLAY = 'drm/license/fairplay',\n DRM_LICENSE_PRIMETIME = 'drm/license/primetime',\n DRM_LICENSE_CLEARKEY = 'drm/license/clearkey',\n DRM_LICENSE_TVKEY = 'drm/license/tvkey',\n\n DRM_CERTIFICATE_FAIRPLAY = 'drm/certificate/fairplay',\n\n KEY_HLS_AES = 'key/hls/aes',\n\n TIME_SYNC = 'time/sync',\n\n WEBRTC_SDP_REQUEST = 'webrtc/sdp/request',\n WEBRTC_SDP_ANSWER = 'webrtc/sdp/answer',\n WEBRTC_SDP_OFFER = 'webrtc/sdp/offer',\n\n UNKNOWN = 'unknown',\n\n INTERNAL = 'internal',\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","import type {Ad, LinearAd, VastAdData} from 'bitmovin-player';\n\nimport * as Utils from '../utils/Utils';\n\nexport class AdSample {\n private static parseSkipAfter(skipAfter?: number) {\n if (skipAfter === undefined) {\n return undefined;\n }\n if (skipAfter === -1) {\n return skipAfter;\n }\n return Utils.calculateTime(skipAfter);\n }\n\n wrapperAdsCount?: number;\n adSkipAfter?: number;\n adSkippable?: boolean;\n adClickthroughUrl?: string;\n adDescription?: string;\n adDuration?: number;\n adId?: string;\n adImpressionId?: string;\n adPlaybackHeight?: number;\n adPlaybackWidth?: number;\n adStartupTime?: number;\n adSystem?: string;\n adTitle?: string;\n advertiserName?: string;\n apiFramework?: string;\n audioBitrate?: number;\n clicked = 0;\n clickPosition?: number;\n closed = 0;\n closePosition?: number;\n completed = 0;\n creativeAdId?: string;\n creativeId?: string;\n dealId?: string;\n isLinear?: boolean;\n mediaPath?: string;\n mediaServer?: string;\n mediaUrl?: string;\n midpoint = 0;\n minSuggestedDuration?: number;\n percentageInViewport?: number;\n quartile1 = 0;\n quartile3 = 0;\n skipped = 0;\n skipPosition?: number;\n started = 0;\n streamFormat?: string;\n surveyUrl?: string;\n time?: number;\n timeHovered?: number;\n timeInViewport?: number;\n timePlayed?: number;\n timeUntilHover?: number;\n universalAdIdRegistry?: string;\n universalAdIdValue?: string;\n videoBitrate?: number;\n adPodPosition?: number;\n exitPosition?: number;\n playPercentage?: number;\n skipPercentage?: number;\n clickPercentage?: number;\n closePercentage?: number;\n errorPosition?: number;\n errorPercentage?: number;\n timeToContent?: number;\n timeFromContent?: number;\n\n constructor(ad?: Ad) {\n if (ad) {\n this.adClickthroughUrl = ad.clickThroughUrl;\n this.adId = ad.id;\n this.mediaUrl = ad.mediaFileUrl;\n const mediaUrlDetails = Utils.getHostnameAndPathFromUrl(this.mediaUrl || '');\n this.mediaPath = mediaUrlDetails.path;\n this.mediaServer = mediaUrlDetails.hostname;\n this.isLinear = ad.isLinear;\n this.adPlaybackHeight = ad.height;\n this.adPlaybackWidth = ad.width;\n\n if (ad.data) {\n this.videoBitrate = ad.data.bitrate === undefined ? undefined : ad.data.bitrate * 1000;\n this.streamFormat = ad.data.mimeType;\n // data.minBitrate\n // data.maxBitrate\n }\n\n const data = ad.data as VastAdData;\n if (data) {\n if (data.adSystem) {\n this.adSystem = data.adSystem.name;\n // this.adSystemVersion = data.adSystem.version;\n }\n if (data.advertiser) {\n this.advertiserName = data.advertiser.name;\n // this.advertiserId = data.advertiser.id;\n }\n // data.codec\n // data.delivery\n // data.pricing\n this.apiFramework = data.apiFramework;\n\n if (data.creative) {\n this.creativeAdId = data.creative.adId;\n this.creativeId = data.creative.id;\n\n if (data.creative.universalAdId) {\n this.universalAdIdRegistry = data.creative.universalAdId.idRegistry;\n this.universalAdIdValue = data.creative.universalAdId.value;\n }\n }\n this.adDescription = data.adDescription;\n this.minSuggestedDuration = Utils.calculateTimeWithUndefined(data.minSuggestedDuration);\n if (data.survey) {\n this.surveyUrl = data.survey.uri;\n // data.survey.type;\n }\n this.adTitle = data.adTitle;\n this.wrapperAdsCount = data.wrapperAdIds ? data.wrapperAdIds.length : 0;\n }\n }\n const linearAd = ad as LinearAd;\n if (linearAd) {\n this.adSkipAfter = AdSample.parseSkipAfter(linearAd.skippableAfter);\n this.adSkippable = linearAd.skippable || (this.adSkipAfter === undefined ? undefined : this.adSkipAfter >= 0);\n this.adDuration = Utils.calculateTime(linearAd.duration);\n }\n }\n}\n","import {FeatureConfigContainer} from './FeatureConfigContainer';\n\nexport interface LicensingRequest {\n key?: string;\n domain: string;\n version: string;\n}\n\nexport enum LicensingResult {\n Denied = 'denied',\n Granted = 'granted',\n Skip = 'skip',\n}\n\nexport interface LicensingResponse {\n status: LicensingResult;\n message: string;\n features?: FeatureConfigContainer;\n}\n\nexport type LicenseCallFunc = (\n key: string,\n domain: string,\n version: string,\n baseUrl: string,\n) => Promise<LicensingResponse>;\n","export const MESSAGE_NAMESPACE = 'urn:x-cast:com.bitmovin.analytics.cast';\nexport const ANALYTICS_BACKEND_BASE_URL = 'https://analytics-ingress-global.bitmovin.com';\n\nexport const ANALYTICS_LICENSECALL_TIMEOUT = 1000 * 60;\nexport const ANALYTICS_VIDEOSTART_TIMEOUT = 1000 * 60; // in milliseconds\n\nexport const ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD = 50;\nexport const ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL = 60 * 60 * 1000;\n\n/**\n * Time (in milliseconds) of consecutive buffering until a REBUFFER_TIMEOUT_ERROR is raised.\n */\nexport const ANALYTICS_REBUFFER_TIMEOUT = 1000 * 60 * 2;\n\n/**\n * minimal time (in seconds) a seek event should have in order to be recogniced as seek\n */\nexport const ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD = 3;\n\n/**\n * Has to be greater or equal than Ingress side limit (currently 1000).\n */\nexport const SEQUENCE_NUMBER_LIMIT = 1000;\n","import type {PlayerAPI, PlayerConfig} from 'bitmovin-player';\n\nimport type {\n AdapterAPI,\n SsaiAdBreakMetadata,\n SsaiAdMetadata,\n SsaiAdQuartile,\n SsaiAdQuartileMetadata,\n SsaiApi,\n} from '../../api/AdapterAPI';\nimport {Analytics} from '../../core/Analytics';\nimport {\n hasValidSsaiAdBreakMetadataStructure,\n hasValidSsaiAdMetadataStructure,\n hasValidSsaiAdQuartileStructure,\n sanitizeSsaiAdQuartileMetadata,\n simplySanitizeSsaiAdBreakMetadata,\n simplySanitizeSsaiAdMetadata,\n} from '../../core/ssai/ssaiApiUtils';\nimport type {AnalyticsConfig} from '../../types/AnalyticsConfig';\nimport type {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport type {CustomDataValues} from '../../types/CustomDataValues';\nimport {guardAgainstDuplicatedUserId, sanitizeAnalyticsConfig} from '../../utils/analyticsConfigUtils';\nimport {logger} from '../../utils/Logger';\nimport {\n hasPlayerAlreadyBeenAugmented,\n isDefined,\n markPlayerInstanceAsAugmented,\n} from '../../utils/playerAugmentationUtils';\nimport {VERSION} from '../../utils/Version';\nimport type {InternalAdapterAPI} from '../internal/InternalAdapterAPI';\n\nimport {sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition} from './bitmovin8AdapterSsaiApiSanitizeUtils';\nimport {Bitmovin8InternalAdapter} from './Bitmovin8InternalAdapter';\n\nexport class Bitmovin8Adapter implements AdapterAPI {\n private readonly internalAdapter: InternalAdapterAPI | undefined;\n private readonly analytics: Analytics | undefined;\n\n constructor(player: any, opts?: AnalyticsStateMachineOptions) {\n if (hasPlayerAlreadyBeenAugmented(player)) {\n logger.errorMessageToUser('Bitmovin Analytics is already hooked up to this player instance');\n return;\n }\n markPlayerInstanceAsAugmented(player);\n\n const playerConfig: PlayerConfig = (player as PlayerAPI).getConfig();\n const sanitizedConfig = sanitizeAnalyticsConfig(playerConfig.analytics as AnalyticsConfig);\n guardAgainstDuplicatedUserId(sanitizedConfig);\n sanitizedConfig.playerKey = sanitizedConfig.playerKey ?? playerConfig.key;\n\n this.internalAdapter = Bitmovin8InternalAdapter.create(player, opts);\n this.analytics = Analytics.create(sanitizedConfig, this.internalAdapter);\n\n // We do this here in order to put the reference of the adapter onto the player\n // customer using the bitmovin adapter standalone might not know that they need to\n // hold a reference\n player.analytics = this;\n\n this.wrapPlayerLoad(player, this.analytics);\n }\n\n readonly ssai: SsaiApi = {\n adBreakStart: (adBreakMetadata?: SsaiAdBreakMetadata) => {\n if (!isDefined(this.internalAdapter)) return;\n\n // quick fix for v2.39.0 missing validation of adPosition\n const adBreakMetadataWithValidAdPosition = sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition(adBreakMetadata);\n\n if (!hasValidSsaiAdBreakMetadataStructure(adBreakMetadataWithValidAdPosition)) {\n // if we don't have valid ad break metadata, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedAdBreakMetadata = simplySanitizeSsaiAdBreakMetadata(adBreakMetadataWithValidAdPosition);\n\n this.internalAdapter.ssaiService.adBreakStart(sanitizedAdBreakMetadata);\n },\n\n adStart: (adMetadata?: SsaiAdMetadata) => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n if (!hasValidSsaiAdMetadataStructure(adMetadata)) {\n // if we don't have valid ad metadata, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedAdMetadata = simplySanitizeSsaiAdMetadata(adMetadata);\n\n this.internalAdapter.ssaiService.adStart(sanitizedAdMetadata);\n // we need to call this here to revert the customData values to the values before the adBreak\n // this is mainly needed to have clear transitions between ads, and we don't\n // copy over customData values from the first ad into the second ad\n // the adMetadata is applied after this call in the manipulate method when a sample is sent\n // it is a bit of a hack, but it is necessary right now due to the way how samples are created\n this.analytics.setConfigParameters();\n this.analytics.setAutoDetectedDeviceInformation();\n },\n\n adQuartileFinished: (adQuartile: SsaiAdQuartile, adQuartileMetadata?: SsaiAdQuartileMetadata) => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n if (!hasValidSsaiAdQuartileStructure(adQuartile)) {\n // if we don't have valid ad quartile, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedSsaiAdQuartileMetadata = sanitizeSsaiAdQuartileMetadata(adQuartileMetadata);\n\n this.internalAdapter.ssaiService.adQuartileFinished(adQuartile, sanitizedSsaiAdQuartileMetadata);\n },\n\n adBreakEnd: () => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n this.internalAdapter.ssaiService.adBreakEnd();\n // we need to call this here to revert the customData values to the values we had before the ad\n this.analytics.setConfigParameters();\n this.analytics.setAutoDetectedDeviceInformation();\n },\n };\n\n /*\n * intercept `player.load` with automated sourceChange handling\n */\n private wrapPlayerLoad(player: PlayerAPI, analytics: Analytics) {\n const originalLoad = player.load;\n player.load = (...args: Parameters<typeof player.load>): Promise<void> => {\n if (args.length > 0) {\n const analyticsConfig = (args[0] as any).analytics;\n // we reset the analytics and reload with a new config\n analytics.sourceChange(analyticsConfig);\n }\n\n return originalLoad.apply(player, args);\n };\n }\n\n static readonly version: string = VERSION;\n\n get version(): string {\n return VERSION;\n }\n\n getCurrentImpressionId(): string | undefined {\n if (!isDefined(this.analytics)) return;\n\n return this.analytics.getCurrentImpressionId();\n }\n\n getUserId(): string | undefined {\n if (!isDefined(this.analytics)) return;\n\n return this.analytics.getUserId();\n }\n\n setCustomData(values: CustomDataValues) {\n if (!isDefined(this.internalAdapter)) return;\n\n this.internalAdapter.setCustomData(values);\n }\n\n setCustomDataOnce(values: CustomDataValues) {\n if (!isDefined(this.analytics)) return;\n\n this.analytics.setCustomDataOnce(values);\n }\n\n sourceChange(config: AnalyticsConfig) {\n if (!isDefined(this.analytics)) return;\n\n this.analytics.sourceChange(config);\n }\n}\n","import type {VideoStartFailedReason} from '../enums/VideoStartFailedReason';\n\nimport type {AnalyticsConfig} from './AnalyticsConfig';\nimport type {CustomDataValues} from './CustomDataValues';\nimport type {AnalyticsEventBase, ErrorEvent} from './EventData';\nimport type {Sample} from './Sample';\n\nexport type HeartbeatPayload = {\n buffered?: Sample['buffered'];\n played?: Sample['played'];\n /** Flag indicating that the event was triggered by SSAI */\n triggeredBySsai?: boolean;\n};\n\nexport interface StateMachineCallbacks {\n setup: (duration: number, state: string) => void;\n startup: (duration: number, state: string) => void;\n playing: (duration: number, state: string) => void;\n heartbeat: (duration: number, state: 'playing' | 'rebuffering', payload: HeartbeatPayload) => void;\n qualitychange: (duration: number, state: string) => void;\n qualitychange_pause: (duration: number, state: string) => void;\n qualitychange_rebuffering: (duration: number, state: string) => void;\n videoChange: (event: any) => void;\n audioChange: (event: any) => void;\n audiotrack_changing: () => void;\n pause: (duration: number, state: string) => void;\n /**\n * Should send a sample with `state: \"seeking\"` and `duration` set to the duration of the seeking.\n */\n seeking: (duration: number) => void;\n /**\n * @deprecated use {@link StateMachineCallbacks.seeking} instead. We should send the samples with `state: \"seeking\"`\n * and not with any custom values like \"paused_seeking\" / \"play_seeking\" / \"seeked\" etc.!\n */\n paused_seeking: (duration: number, state: string) => void;\n /**\n * @deprecated use {@link StateMachineCallbacks.seeking} instead. We should send the samples with `state: \"seeking\"`\n * and not with any custom values like \"paused_seeking\" / \"play_seeking\" / \"seeked\" etc.!\n */\n end_play_seeking: (duration: number, state: string) => void;\n rebuffering: (duration: number, state: string) => void;\n error: (event: Readonly<ErrorEvent>) => void;\n end: (duration: number, state: string) => void;\n unload: (duration: number, state: string) => void;\n ad: (duration: number, state: string) => void;\n mute: () => void;\n unMute: () => void;\n subtitle_changing: () => void;\n setVideoTimeEndFromEvent: (event: any | AnalyticsEventBase) => void;\n setVideoTimeStartFromEvent: (event: any | AnalyticsEventBase) => void;\n videoStartFailed: (duration: number, reason: VideoStartFailedReason) => void;\n startCasting: (duration: number, event: any) => void;\n casting: (duration: number, event: any) => void;\n manualSourceChange: (event: {config: AnalyticsConfig}) => void;\n initialSourceChange: (event: {config: AnalyticsConfig}) => void;\n muting_ready: (duration: number, state: string, event: any) => void;\n customdatachange: (duration?: number, state?: string, event?: {values: CustomDataValues}) => void;\n\n /** shuts down the collection and removes/clears all timeouts, intervals, event listeners */\n release: () => void;\n playlistTransition: (event: Readonly<AnalyticsEventBase>) => void;\n}\n\n/**\n * {@link StateMachineCallbacks} object with each callback set to be empty function (doing nothing).\n *\n * Why?:\n * We need to set it as default value in {@link InternalAdapter} for use case, when {@link InternalAdapter}\n * is already created and listen to player events, but {@link Analytics} was not instantiated/initialized yet (that\n * should set correct {@link StateMachineCallbacks} implementation)\n */\nexport const defaultStateMachineCallbacks: StateMachineCallbacks = {\n setup: () => {},\n startup: () => {},\n playing: () => {},\n heartbeat: () => {},\n qualitychange: () => {},\n qualitychange_pause: () => {},\n qualitychange_rebuffering: () => {},\n videoChange: () => {},\n audioChange: () => {},\n audiotrack_changing: () => {},\n pause: () => {},\n seeking: () => {},\n paused_seeking: () => {},\n end_play_seeking: () => {},\n rebuffering: () => {},\n error: () => {},\n end: () => {},\n unload: () => {},\n ad: () => {},\n mute: () => {},\n unMute: () => {},\n subtitle_changing: () => {},\n setVideoTimeEndFromEvent: () => {},\n setVideoTimeStartFromEvent: () => {},\n videoStartFailed: () => {},\n startCasting: () => {},\n casting: () => {},\n manualSourceChange: () => {},\n initialSourceChange: () => {},\n muting_ready: () => {},\n customdatachange: () => {},\n release: () => {},\n playlistTransition: () => {},\n};\n","import type {CodecInfo} from '../types/CodecInfo';\nimport type {PlaybackInfo} from '../types/PlaybackInfo';\nimport {isBlank} from '../utils/stringUtils';\nimport {isNotNullish} from '../utils/Utils';\n\n/**\n * This class is used to store source specific information for the player\n * mainly as a fallback if sourceInfo cannot be determined by the player since the source is already unloaded\n */\nexport class SourceInfoFallbackService {\n private streamFormat: PlaybackInfo['streamFormat'];\n private audioCodec: PlaybackInfo['audioCodec'];\n private videoCodec: PlaybackInfo['videoCodec'];\n\n reset() {\n this.streamFormat = undefined;\n this.audioCodec = undefined;\n this.videoCodec = undefined;\n }\n\n setStreamFormat(streamFormat: PlaybackInfo['streamFormat']) {\n this.streamFormat = streamFormat;\n }\n\n applyStreamFormat(playbackInfo: PlaybackInfo) {\n if (isBlank(this.streamFormat)) {\n return;\n }\n playbackInfo.streamFormat = this.streamFormat;\n }\n\n /**\n * Apply fallback values to {@link PlaybackInfo} if available.\n * If provided {@link CodecInfo} values are available, we store them as new fallback values, before we apply them.\n */\n applyAndStoreCodecInfo(playbackInfo: PlaybackInfo, codecInfo: CodecInfo | undefined) {\n if (isNotNullish(codecInfo?.audioCodec)) {\n this.audioCodec = codecInfo.audioCodec;\n }\n if (isNotNullish(codecInfo?.videoCodec)) {\n this.videoCodec = codecInfo.videoCodec;\n }\n\n if (!isBlank(this.audioCodec)) {\n playbackInfo.audioCodec = this.audioCodec;\n }\n if (!isBlank(this.videoCodec)) {\n playbackInfo.videoCodec = this.videoCodec;\n }\n }\n}\n","declare global {\n /** Variable is defined by webpack.DefinePlugin during the build process. */\n const __VERSION__: string;\n}\n\nexport const VERSION: string = __VERSION__;\n","export const setCookie = (\n name: string,\n value: string,\n attributes?: {domain?: string; expires?: string; maxAge?: number},\n): void => {\n let newCookie = name + '=' + value + '; path=/';\n\n if (attributes?.domain) {\n newCookie += `; domain=${attributes.domain}`;\n }\n\n if (attributes?.expires) {\n newCookie += `; expires=${attributes.expires}`;\n }\n\n if (attributes?.maxAge) {\n newCookie += `; max-age=${attributes.maxAge}`;\n }\n\n document.cookie = newCookie;\n};\n\n/** @see https://www.w3schools.com/js/js_cookies.asp */\nexport const getCookie = (cname: string): string => {\n const name = cname + '=';\n const allCookies = document.cookie.split(';');\n for (const c of allCookies) {\n let cookie = c;\n while (cookie.charAt(0) === ' ') {\n cookie = cookie.substring(1); //trim spaces (if any) between ';' and next attribute\n }\n if (cookie.indexOf(name) === 0) {\n return cookie.substring(name.length, c.length);\n }\n }\n return '';\n};\n\n/** @see https://www.w3schools.com/js/js_cookies.asp */\nexport const deleteCookie = (cname: string): void => {\n document.cookie = `${cname}=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;`;\n};\n","import {PAGE_LOAD_TYPE} from '../enums/PageLoadType';\nimport type {CustomDataValues} from '../types/CustomDataValues';\nimport * as CustomDataUtils from '../types/CustomDataValues';\n\nimport {endsWith, startsWith} from './stringUtils';\n\n/**\n * Performs a loose equality check (==), which means it checks for both null and undefined.\n *\n * @returns {value is null | undefined} `true` if the given value is `null` or `undefined`.\n */\nexport const isNullish = (value: unknown): value is null | undefined => value == null;\n\n/**\n *\n * @returns {value is Exclude<unknown, null | undefined>} `true` if the given value is not `null` and is not `undefined`.\n */\nexport const isNotNullish = <T = unknown>(value: T): value is Exclude<T, null | undefined> => !isNullish(value);\n\n/**\n * @returns {value is boolean} `true` if the given value is {@link isNotNullish} and is type of `boolean`.\n */\nexport const isBoolean = (value: unknown): value is boolean => !isNullish(value) && typeof value === 'boolean';\n\nexport const toBoolean = (value: unknown): boolean => Boolean(value).valueOf();\n\n/**\n * @returns {value is number} `true` if the given value is {@link isNotNullish} and is type of `number`.\n */\nexport const isNumber = (value: unknown): value is number => !isNullish(value) && typeof value === 'number';\n\n/**\n * Checks if a value is a non-null object.\n *\n * We must exclude `null` explicitly, because `typeof null === \"object\"`\n *\n * @returns {value is Record<string, unknown>} `true` if the value is a non-null object, otherwise `false`.\n */\nexport const isObject = <T extends object>(value: T): value is T => {\n return isNotNullish(value) && typeof value === 'object';\n};\n\n/**\n * Checks if a value is a plain object (not an array, function, or built-in instance).\n *\n * @returns {value is Record<string, unknown>} `true` if the value is a plain object, otherwise `false`.\n */\nexport const isPlainObject = <T extends object>(value: T): value is T => {\n return Object.prototype.toString.call(value) === '[object Object]';\n};\n\nexport const sanitizePath = (path: string): string => {\n return path.replace(/\\/$/g, '');\n};\n\nexport const calculateTimeWithUndefined = (time?: number): number | undefined => {\n if (time === undefined) {\n return time;\n }\n time = time * 1000;\n return Math.round(time);\n};\n\nexport const calculateTime = (time: number): number => {\n time = time * 1000;\n return Math.round(time);\n};\n\n/**\n * @deprecated Use directly `Date.now()` instead\n *\n * Return the current time in milliseconds.\n */\nexport const getCurrentTimestamp = (): number => {\n return Date.now();\n};\n\n/**\n * Empty function returns undefined\n *\n * @deprecated\n */\nexport const noOp = () => undefined;\n\nexport const getCustomDataString = (customData: any): string | undefined => {\n if (typeof customData === 'object') {\n return JSON.stringify(customData);\n } else if (typeof customData === 'function') {\n return getCustomDataString(customData());\n } else if (typeof customData === 'undefined') {\n return customData;\n } else if (typeof customData !== 'string') {\n return String(customData);\n }\n\n return customData;\n};\n\nexport const transferCustomDataFields = (fromConfig: CustomDataValues, toConfig: CustomDataValues) => {\n for (let i = 1; i <= CustomDataUtils.customDataFieldCount; i++) {\n const customDataField = `customData${i}`;\n toConfig[customDataField] = getCustomDataString(fromConfig[customDataField]);\n }\n};\n\nexport const getDocumentPropWithPrefix = (prop: string): string | undefined => {\n const prefixes = ['webkit', 'moz', 'ms', 'o'];\n if (prop in document) {\n return prop;\n }\n\n const pascalCase = prop.charAt(0).toUpperCase() + prop.slice(1);\n for (const prefix of prefixes) {\n if (prefix + pascalCase in document) {\n return prefix + pascalCase;\n }\n }\n return undefined;\n};\n\nexport const isVideoInFullscreen = () => {\n const fullscreenProp = getDocumentPropWithPrefix('fullscreenElement');\n return fullscreenProp !== undefined && document[fullscreenProp] && document[fullscreenProp].nodeName === 'VIDEO';\n};\n\nexport const getHiddenProp = (): string | undefined => {\n return getDocumentPropWithPrefix('hidden');\n};\n\nexport function getPageLoadType(): PAGE_LOAD_TYPE {\n const hiddenProp = getHiddenProp();\n if (isNotNullish(hiddenProp) && document[hiddenProp] === true) {\n return PAGE_LOAD_TYPE.BACKGROUND;\n }\n return PAGE_LOAD_TYPE.FOREGROUND;\n}\n\nexport const getHostnameAndPathFromUrl = (url: string) => {\n const domElement = document.createElement('a');\n domElement.href = url;\n\n return {hostname: domElement.hostname, path: domElement.pathname};\n};\n\nexport const calculatePercentage = (numerator?: number, denominator?: number): number | undefined => {\n if (denominator === undefined || denominator === 0) {\n return undefined;\n }\n return Math.round(((numerator || 0) / denominator) * 100);\n};\n\nexport const getURLResourceName = (url: string): string => {\n if (url.length === 0) {\n return '';\n }\n return url.split('/').pop() || '';\n};\n\nexport const joinUrls = (...args: string[]): string => {\n return args.reduce((prev, current) => {\n const prevUrlValue = endsWith(prev, '/') && current !== undefined ? prev.substr(0, prev.length - 1) : prev;\n const nextUrlValue = startsWith(current, '/') ? current.substr(1) : current;\n return prevUrlValue + '/' + nextUrlValue;\n });\n};\n","import {ProgressiveSourceConfig} from '../types/ProgressiveSourceConfig';\nimport {ProgressiveSourceInfo} from '../types/SourceInfo';\n\nimport {isNotNullish} from './Utils';\n\nexport const getSourceInfoFromBitmovinSourceConfig = (\n progressive: ProgressiveSourceConfig,\n player: any,\n): ProgressiveSourceInfo => {\n if (!progressive) {\n return {\n progBitrate: undefined,\n progUrl: undefined,\n };\n }\n\n if (typeof progressive === 'string') {\n return {\n progBitrate: 0,\n progUrl: progressive,\n };\n }\n\n if (Array.isArray(progressive) && progressive.length > 0) {\n const playbackVideoData = player.getPlaybackVideoData();\n let progressiveArrayIndex = 0;\n\n if (isNotNullish(playbackVideoData) && !isNaN(+playbackVideoData.id)) {\n progressiveArrayIndex = +playbackVideoData.id;\n }\n\n return {\n progBitrate: progressive[progressiveArrayIndex].bitrate || 0,\n progUrl: progressive[progressiveArrayIndex].url,\n };\n }\n\n if (typeof progressive === 'object' && !Array.isArray(progressive)) {\n return {\n progBitrate: progressive.bitrate || 0,\n progUrl: progressive.url,\n };\n }\n\n return {\n progBitrate: undefined,\n progUrl: undefined,\n };\n};\n","import {LicensingResponse} from '../types/LicensingRequest';\n\nimport {post} from './Http';\nimport {joinUrls} from './Utils';\n\nexport function LicenseCall(key: string, domain: string, version: string, baseUrl: string): Promise<LicensingResponse> {\n const licenseServerUrl = joinUrls(baseUrl, '/licensing');\n const licensingRequest = {\n analyticsVersion: version,\n domain,\n key,\n };\n\n return new Promise<LicensingResponse>((resolve) => {\n post(licenseServerUrl, licensingRequest, (response) => {\n resolve(response);\n });\n });\n}\n","import {appendSsaiRoutingParam, isSsaiRelatedSample} from '../core/ssai/ssaiUtils';\nimport type {AdSample, Sample} from '../types/Sample';\n\nimport {post} from './Http';\nimport {joinUrls, noOp} from './Utils';\n\nexport class AnalyticsCall {\n private readonly analyticsServerUrl: string;\n private readonly adAnalyticsServerUrl: string;\n\n constructor(baseUrl: string) {\n this.analyticsServerUrl = joinUrls(baseUrl, 'analytics');\n this.adAnalyticsServerUrl = joinUrls(baseUrl, 'analytics/a');\n }\n\n sendRequest(sample: Sample, callback: () => void) {\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n post(analyticsUrl, sample, callback);\n }\n\n sendUnloadRequest(sample: Sample) {\n const sendBeaconFallback = (data: Sample) => this.sendRequestSynchronous(data, noOp);\n\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n this.trySendBeacon(sendBeaconFallback, analyticsUrl, sample);\n }\n\n private trySendBeacon(\n fallbackFunction: (data: any) => void,\n url: string,\n data: unknown,\n requestHeaders: {[headerName: string]: string} = {},\n ) {\n if (typeof navigator.sendBeacon === 'undefined') {\n fallbackFunction(data);\n } else {\n /**\n * With a Blob we can send payload but also http headers\n * @see https://stackoverflow.com/questions/40523469/navigator-sendbeacon-to-pass-header-information\n */\n const blob = new Blob([JSON.stringify(data)], requestHeaders);\n const success = navigator.sendBeacon(url, blob);\n if (!success) {\n fallbackFunction(data);\n }\n }\n }\n\n sendRequestSynchronous(sample: Sample, callback: () => void) {\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n post(analyticsUrl, sample, callback, false);\n }\n\n sendAdRequest(adSample: AdSample) {\n let adAnalyticsUrl = this.adAnalyticsServerUrl;\n if (isSsaiRelatedSample(adSample)) {\n adAnalyticsUrl = appendSsaiRoutingParam(adAnalyticsUrl);\n }\n\n const sendBeaconFallback = (data: AdSample) => post(adAnalyticsUrl, data, noOp);\n this.trySendBeacon(sendBeaconFallback, adAnalyticsUrl, adSample);\n }\n}\n","export class AdCallbacks {\n onAdStarted = (_event: any): void => undefined;\n onAdFinished = (_event: any): void => undefined;\n onAdBreakStarted = (_event: any): void => undefined;\n onAdBreakFinished = (_event: any): void => undefined;\n onAdClicked = (_event: any): void => undefined;\n onAdError = (_event: any): void => undefined;\n onAdManifestLoaded = (_event: any): void => undefined;\n onAdQuartile = (_event: any): void => undefined;\n onAdSkipped = (_event: any): void => undefined;\n onPlay = (_issuer?: string): void => undefined;\n onPause = (_issuer?: string): void => undefined;\n onBeforeUnload = (): void => undefined;\n}\n\nexport interface AdModuleAPI {\n readonly adCallbacks: AdCallbacks;\n isLinearAdActive: () => boolean;\n getContainer: () => HTMLElement;\n getAdModuleInfo: () => {name?: string; version?: string};\n currentTime: () => number;\n}\n","export interface CustomDataValues {\n customData1?: string;\n customData2?: string;\n customData3?: string;\n customData4?: string;\n customData5?: string;\n customData6?: string;\n customData7?: string;\n customData8?: string;\n customData9?: string;\n customData10?: string;\n customData11?: string;\n customData12?: string;\n customData13?: string;\n customData14?: string;\n customData15?: string;\n customData16?: string;\n customData17?: string;\n customData18?: string;\n customData19?: string;\n customData20?: string;\n customData21?: string;\n customData22?: string;\n customData23?: string;\n customData24?: string;\n customData25?: string;\n customData26?: string;\n customData27?: string;\n customData28?: string;\n customData29?: string;\n customData30?: string;\n customData31?: string;\n customData32?: string;\n customData33?: string;\n customData34?: string;\n customData35?: string;\n customData36?: string;\n customData37?: string;\n customData38?: string;\n customData39?: string;\n customData40?: string;\n customData41?: string;\n customData42?: string;\n customData43?: string;\n customData44?: string;\n customData45?: string;\n customData46?: string;\n customData47?: string;\n customData48?: string;\n customData49?: string;\n customData50?: string;\n experimentName?: string;\n}\n\n/**\n * Lists all keys of the {@see CustomDataValues} interface.\n */\nexport const customDataValuesKeys: Array<keyof CustomDataValues> = [\n 'customData1',\n 'customData2',\n 'customData3',\n 'customData4',\n 'customData5',\n 'customData6',\n 'customData7',\n 'customData8',\n 'customData9',\n 'customData10',\n 'customData11',\n 'customData12',\n 'customData13',\n 'customData14',\n 'customData15',\n 'customData16',\n 'customData17',\n 'customData18',\n 'customData19',\n 'customData20',\n 'customData21',\n 'customData22',\n 'customData23',\n 'customData24',\n 'customData25',\n 'customData26',\n 'customData27',\n 'customData28',\n 'customData29',\n 'customData30',\n 'customData31',\n 'customData32',\n 'customData33',\n 'customData34',\n 'customData35',\n 'customData36',\n 'customData37',\n 'customData38',\n 'customData39',\n 'customData40',\n 'customData41',\n 'customData42',\n 'customData43',\n 'customData44',\n 'customData45',\n 'customData46',\n 'customData47',\n 'customData48',\n 'customData49',\n 'customData50',\n\n 'experimentName',\n];\n\n/**\n * The number of CustomDataXX fields in {@see CustomDataValues}.\n */\nexport const customDataFieldCount = customDataValuesKeys.filter((i) => i.match('customData\\\\d+')).length;\n\nexport const extractCustomDataFieldsOnly = (input: CustomDataValues): CustomDataValues => {\n const retVal: CustomDataValues = {};\n customDataValuesKeys.forEach((key) => {\n if (input[key]) {\n retVal[key] = input[key];\n }\n });\n return retVal;\n};\n","export class Converter {\n static bytesToBits(bytes: number): number {\n return bytes * 8;\n }\n static bitsToBytes(bits: number): number {\n return Math.round(bits / 8);\n }\n static kiloBitsToBits(kiloBits: number): number {\n return kiloBits * 1000;\n }\n}\n","import * as Utils from '../utils/Utils';\n\nimport {CustomDataValues} from './CustomDataValues';\nimport {Sample} from './Sample';\n\nexport class AdAnalyticsSample implements CustomDataValues {\n adModule?: string;\n adModuleVersion?: string;\n videoImpressionId?: string;\n userAgent?: string;\n language?: string;\n cdnProvider?: string;\n customData1?: string;\n customData2?: string;\n customData3?: string;\n customData4?: string;\n customData5?: string;\n customData6?: string;\n customData7?: string;\n customData8?: string;\n customData9?: string;\n customData10?: string;\n customData11?: string;\n customData12?: string;\n customData13?: string;\n customData14?: string;\n customData15?: string;\n customData16?: string;\n customData17?: string;\n customData18?: string;\n customData19?: string;\n customData20?: string;\n customData21?: string;\n customData22?: string;\n customData23?: string;\n customData24?: string;\n customData25?: string;\n customUserId?: string;\n experimentName?: string;\n domain?: string;\n key?: string;\n path?: string;\n player?: string;\n playerKey?: string;\n playerTech?: string;\n screenHeight?: number;\n screenWidth?: number;\n version?: string;\n size?: string;\n userId?: string;\n videoId?: string;\n videoTitle?: string;\n videoWindowHeight?: number;\n videoWindowWidth?: number;\n playerStartupTime?: number;\n analyticsVersion?: string;\n pageLoadTime?: number;\n pageLoadType?: number;\n autoplay?: boolean;\n platform = 'web';\n audioCodec?: string;\n videoCodec?: string;\n\n constructor(sample?: Sample) {\n if (!sample) {\n return;\n }\n this.videoImpressionId = sample.impressionId;\n this.userAgent = sample.userAgent;\n this.language = sample.language;\n this.cdnProvider = sample.cdnProvider;\n\n Utils.transferCustomDataFields(sample, this);\n\n this.customUserId = sample.customUserId;\n this.domain = sample.domain;\n this.experimentName = sample.experimentName;\n this.key = sample.key;\n this.path = sample.path;\n this.player = sample.player;\n this.playerKey = sample.playerKey;\n this.playerTech = sample.playerTech;\n this.screenHeight = sample.screenHeight;\n this.screenWidth = sample.screenWidth;\n this.version = sample.version;\n this.size = sample.size;\n this.userId = sample.userId;\n this.videoId = sample.videoId;\n this.videoTitle = sample.videoTitle;\n this.videoWindowHeight = sample.videoWindowHeight;\n this.videoWindowWidth = sample.videoWindowWidth;\n this.audioCodec = sample.audioCodec;\n this.videoCodec = sample.videoCodec;\n }\n}\n","export enum CastTech {\n AirPlay = 'AirPlay',\n GoogleCast = 'GoogleCast',\n WebSocket = 'WebSocket',\n}\n","import {SegmentInfo} from '../types/SegmentInfo';\n\nexport class SegmentTracker {\n protected segments: SegmentInfo[];\n\n constructor() {\n this.segments = [];\n }\n\n reset(): void {\n this.segments = [];\n }\n\n addSegment(segment: SegmentInfo): void {\n this.segments.push(segment);\n }\n\n removeSegment(url: string): void {\n this.segments = this.segments.filter((s) => s.url !== url);\n }\n\n getSegments(): SegmentInfo[] {\n return this.segments;\n }\n}\n","import type {\n AdPosition,\n SsaiAdBreakMetadata,\n SsaiAdMetadata,\n SsaiAdQuartile,\n SsaiAdQuartileMetadata,\n} from '../../api/AdapterAPI';\nimport {CustomDataValues, extractCustomDataFieldsOnly} from '../../types/CustomDataValues';\nimport {logger} from '../../utils/Logger';\nimport {isValidString} from '../../utils/stringUtils';\nimport {isNotNullish, isNullish, isPlainObject, transferCustomDataFields} from '../../utils/Utils';\n\nexport function isAdPosition(anything: unknown): anything is AdPosition {\n // invalid, when not defined as one of string values we expect\n return anything === 'preroll' || anything === 'midroll' || anything === 'postroll';\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdBreakMetadataStructure(\n anything: unknown,\n): anything is SsaiAdBreakMetadata | null | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(anything)) return true;\n\n // invalid, when value was defined, but not as a plain object\n if (!isPlainObject(anything as object)) {\n logger.errorMessageToUser('Invalid SsaiAdBreakMetadata: not a plain object');\n return false;\n }\n\n const maybeSsaiAdBreakMetadata = anything as SsaiAdBreakMetadata;\n\n // invalid, when `adPosition` was defined, but not as an ad position string we expect\n if (isNotNullish(maybeSsaiAdBreakMetadata.adPosition) && !isAdPosition(maybeSsaiAdBreakMetadata.adPosition)) {\n logger.errorMessageToUser(\"Invalid SsaiAdBreakMetadata: 'adPosition' property is not valid\");\n return false;\n }\n\n return true;\n}\n\n/**\n * Simple sanitization of {@link SsaiAdBreakMetadata} without object structure check,\n * because {@link hasValidSsaiAdBreakMetadataStructure} should be called before in adapter SSAI API function!\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return `undefined`\n * - recreate a new object to avoid side effects by using same reference from outside\n *\n * @param adBreakMetadata SsaiAdBreakMetadata or `undefined` (optional SSAI API parameter)\n */\nexport function simplySanitizeSsaiAdBreakMetadata(\n adBreakMetadata: SsaiAdBreakMetadata | undefined,\n): SsaiAdBreakMetadata | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(adBreakMetadata)) {\n // sanitize to use `undefined` in code\n return undefined;\n }\n\n // recreate a new object\n return {\n adPosition: adBreakMetadata.adPosition,\n };\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdMetadataStructure(anything: unknown): anything is SsaiAdMetadata | null | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(anything)) {\n return true;\n }\n\n // invalid, when value was defined, but not as a plain object\n if (!isPlainObject(anything as object)) {\n logger.errorMessageToUser('Invalid SsaiAdMetadata: not a plain object');\n return false;\n }\n\n const maybeSsaiAdMetadata = anything as SsaiAdMetadata;\n\n // invalid, when `adId` was defined, but not as a string\n if (isNotNullish(maybeSsaiAdMetadata.adId) && !isValidString(maybeSsaiAdMetadata.adId)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'adId' property is not string\");\n return false;\n }\n\n // invalid, when `adSystem` was defined, but not as a string\n if (isNotNullish(maybeSsaiAdMetadata.adSystem) && !isValidString(maybeSsaiAdMetadata.adSystem)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'adSystem' property is not string\");\n return false;\n }\n\n // invalid, when `customData` was defined, but not as an object\n if (isNotNullish(maybeSsaiAdMetadata.customData) && !isPlainObject(maybeSsaiAdMetadata.customData)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'customData' property is not a plain object\");\n return false;\n }\n\n return true;\n}\n\n/**\n * Simple sanitization of {@link SsaiAdMetadata} without object structure check,\n * because {@link hasValidSsaiAdMetadataStructure} should be called before in adapter SSAI API function!\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return `undefined`\n * - recreate a new object to avoid side effects by using same reference from outside\n *\n * @param ssaiAdMetadata SsaiAdMetadata or `undefined` (optional SSAI API parameter)\n */\nexport function simplySanitizeSsaiAdMetadata(ssaiAdMetadata: SsaiAdMetadata | undefined): SsaiAdMetadata | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(ssaiAdMetadata)) {\n // sanitize to use `undefined` in code\n return undefined;\n }\n\n let sanitizedCustomDataValues: CustomDataValues | undefined = undefined;\n\n // we are extracting the customData fields explicitly to make sure that there is not a different object passed\n if (isNotNullish(ssaiAdMetadata.customData)) {\n const extracted = extractCustomDataFieldsOnly(ssaiAdMetadata.customData);\n sanitizedCustomDataValues = {};\n transferCustomDataFields(extracted, sanitizedCustomDataValues);\n }\n\n // recreate a new object\n return {\n adId: ssaiAdMetadata.adId,\n adSystem: ssaiAdMetadata.adSystem,\n customData: sanitizedCustomDataValues,\n };\n}\n\nexport function isSsaiAdQuartile(anything: unknown): anything is SsaiAdQuartile {\n return anything === 'first' || anything === 'midpoint' || anything === 'third' || anything === 'completed';\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdQuartileStructure(anything: unknown): anything is SsaiAdQuartile {\n if (!isSsaiAdQuartile(anything)) {\n logger.errorMessageToUser('Invalid SsaiAdQuartile');\n return false;\n }\n\n return true;\n}\n\n/**\n * Full sanitization of unknown customer input.\n * We sanitize correct object structure and print user error messages for incorrect input.\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return empty object `{}`\n * - if NOT `typeof 'object'` is passed, it will return empty object `{}` and print user error message\n * - recreate a new object to avoid side effects by using same reference from outside\n * - if `failedBeaconUrl` is not valid string, we use `undefined` and print user error message\n * - if `failedBeaconUrl` is longer than 500 characters, we cut it\n *\n * @param anything Can be anything, as it is coming from customer JavaScript code\n */\nexport function sanitizeSsaiAdQuartileMetadata(anything: unknown): SsaiAdQuartileMetadata {\n if (isNullish(anything)) {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n // sanitize to plain object to not use nullish value in code\n return {};\n }\n\n if (!isPlainObject(anything as object)) {\n // if NOT a plain object, we return empty plain object and print user error message\n logger.errorMessageToUser('Invalid SsaiAdQuartileMetadata: not a plain object');\n return {};\n }\n\n const maybeSsaiAdQuartileMetadata = anything as SsaiAdQuartileMetadata;\n\n // recreate a new object\n const ssaiAdQuartileMetadata: SsaiAdQuartileMetadata = {\n failedBeaconUrl: maybeSsaiAdQuartileMetadata.failedBeaconUrl,\n };\n\n if (!isValidString(ssaiAdQuartileMetadata.failedBeaconUrl)) {\n logger.errorMessageToUser(\"Invalid SsaiAdQuartileMetadata: 'failedBeaconUrl' property is not string\");\n ssaiAdQuartileMetadata.failedBeaconUrl = undefined;\n } else {\n ssaiAdQuartileMetadata.failedBeaconUrl = ssaiAdQuartileMetadata.failedBeaconUrl.substring(0, 500);\n }\n\n return ssaiAdQuartileMetadata;\n}\n","import type {\n AudioPlaybackQualityChangedEvent,\n PlayerAPI,\n PlayerEventBase,\n SeekEvent,\n UserInteractionEvent,\n VideoPlaybackQualityChangedEvent,\n} from 'bitmovin-player';\n\nimport {Bitmovin8AnalyticsStateMachine} from '../../analyticsStateMachines/bitmovin8/Bitmovin8AnalyticsStateMachine';\nimport {Analytics} from '../../core/Analytics';\nimport {DownloadSpeedMeter} from '../../core/DownloadSpeedMeter';\nimport {HeartbeatService} from '../../core/HeartbeatService';\nimport {SegmentTracker} from '../../core/SegmentTracker';\nimport {SourceInfoFallbackService} from '../../core/SourceInfoFallbackService';\nimport VideoCompletionTracker from '../../core/VideoCompletionTracker';\nimport {CastTech} from '../../enums/CastTech';\nimport {ErrorCode} from '../../enums/ErrorCode';\nimport {Event} from '../../enums/Event';\nimport {Player} from '../../enums/Player';\nimport {PlayerSize} from '../../enums/PlayerSize';\nimport {ErrorDetailBackend} from '../../features/errordetails/ErrorDetailBackend';\nimport {ErrorDetailTracking} from '../../features/errordetails/ErrorDetailTracking';\nimport {Feature} from '../../features/Feature';\nimport {FeatureConfig} from '../../features/FeatureConfig';\nimport {HttpRequestTracking} from '../../features/httprequesttracking/HttpRequestTracking';\nimport {AnalyticsConfig} from '../../types/AnalyticsConfig';\nimport {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {DownloadSpeedInfo} from '../../types/DownloadSpeedInfo';\nimport {DrmPerformanceInfo} from '../../types/DrmPerformanceInfo';\nimport type {AnalyticsEventBase} from '../../types/EventData';\nimport {FeatureConfigContainer} from '../../types/FeatureConfigContainer';\nimport {normalizeVideoDuration, PlaybackInfo} from '../../types/PlaybackInfo';\nimport {SegmentInfo} from '../../types/SegmentInfo';\nimport {getSourceInfoFromBitmovinSourceConfig} from '../../utils/BitmovinProgressiveSourceHelper';\nimport {logger} from '../../utils/Logger';\nimport * as AnalyticsSettings from '../../utils/Settings';\nimport {isNotNullish, isNullish} from '../../utils/Utils';\nimport {AdModuleAPI} from '../internal/ads/AdModuleAPI';\nimport {InternalAdapter} from '../internal/InternalAdapter';\nimport {InternalAdapterAPI} from '../internal/InternalAdapterAPI';\n\nimport {Bitmovin8AdModule} from './Bitmovin8AdModule';\nimport {HttpRequestTrackingAdapter} from './player/HttpRequestTrackingAdapter';\nimport {SegmentTrackerAdapter} from './player/SegmentTrackerAdapter';\nimport {SpeedMeterAdapter} from './player/SpeedMeterAdapter';\n\nenum ViewMode {\n Fullscreen = 'fullscreen',\n Inline = 'inline',\n PictureInPicture = 'pictureinpicture',\n}\n\nexport class Bitmovin8InternalAdapter extends InternalAdapter implements InternalAdapterAPI {\n override get downloadSpeedInfo(): DownloadSpeedInfo {\n return this.speedMeter.getInfo();\n }\n\n override get segments(): SegmentInfo[] {\n return this.segmentTracker.getSegments();\n }\n\n get adModule(): AdModuleAPI | undefined {\n return this._adModule;\n }\n\n get supportsDeferredLicenseLoading(): boolean {\n return true;\n }\n\n /** Boolean flag to prevent multiple calls of the {@link Event.UNLOAD} event */\n private onBeforeUnLoadEvent = false;\n private _adModule?: AdModuleAPI;\n private lastTrackedCurrentTime: number | undefined;\n private videoDuration: number | undefined;\n\n constructor(\n private player: PlayerAPI,\n private speedMeter: DownloadSpeedMeter,\n private segmentTracker: SegmentTracker,\n readonly videoCompletionTracker: VideoCompletionTracker,\n private httpRequestTrackingAdapter: HttpRequestTrackingAdapter,\n sourceInfoFallbackService: SourceInfoFallbackService,\n opts?: AnalyticsStateMachineOptions,\n ) {\n super(opts);\n const playingHeartbeatService = new HeartbeatService(() => player.getCurrentTime());\n const stateMachine = new Bitmovin8AnalyticsStateMachine(\n this.stateMachineCallbacks,\n playingHeartbeatService,\n this.opts,\n );\n playingHeartbeatService.setListener(stateMachine);\n this.sourceInfoFallbackService = sourceInfoFallbackService;\n\n this.stateMachine = stateMachine;\n }\n\n protected get currentTime(): number {\n try {\n // during ad this.player.getCurrentTime() returns time of ad and not video\n // this then messes with videotime_start and videotime_end measurements of video\n // we don't track videotimes for ads\n if (isNotNullish(this.player?.getCurrentTime) && !this.isAdPlaying) {\n return this.player.getCurrentTime();\n }\n } catch {\n logger.warn('Analytics Collector attempted to access player, but player is not available anymore');\n }\n return this.lastTrackedCurrentTime ? this.lastTrackedCurrentTime : 0;\n }\n\n protected get isAdPlaying(): boolean {\n const currentAd = this.player.ads && this.player.ads.getActiveAd();\n return isNotNullish(currentAd);\n }\n\n initialize(analytics: Analytics): Array<Feature<FeatureConfigContainer, FeatureConfig>> {\n this.registerPlayerEventListeners();\n this.registerUnloadEventListeners();\n\n this._adModule = new Bitmovin8AdModule(this.player, this.windowEventTracker);\n\n this.ssaiService.activate({\n getPlayerCurrentTime: () => this.currentTime,\n reportEngagementInteraction: (ssaiEngagementInteractionData) => {\n analytics.sendSsaiEngagementAdSample(ssaiEngagementInteractionData);\n },\n reportPlaybackInteraction: (timestamp: number, eventData: AnalyticsEventBase) =>\n this.stateMachine.onSsaiPlaybackInteraction(timestamp, eventData),\n });\n\n const requestTracking = new HttpRequestTracking([this.httpRequestTrackingAdapter]);\n const errorDetailTracking = new ErrorDetailTracking(\n analytics.errorDetailTrackingSettingsProvider,\n new ErrorDetailBackend(analytics.errorDetailTrackingSettingsProvider.collectorConfig),\n [analytics.errorDetailSubscribable],\n requestTracking,\n );\n return [errorDetailTracking];\n }\n\n override clearValues(): void {\n this.speedMeter.reset();\n }\n\n override clearSegments(): void {\n this.segmentTracker.reset();\n }\n\n override resetSourceRelatedState(): void {\n this.ssaiService.resetSourceRelatedState();\n super.resetSourceRelatedState();\n }\n\n getPlayerVersion = () => this.player.version;\n getPlayerName = () => Player.BITMOVIN;\n getPlayerTech = () => this.player.getPlayerType();\n getAutoPlay(): boolean {\n if (this.player.getConfig().playback) {\n return (this.player.getConfig() as any).playback.autoplay || false;\n }\n return false;\n }\n getDrmPerformanceInfo = (): DrmPerformanceInfo | undefined => this.drmPerformanceInfo;\n\n getCurrentPlaybackInfo(): PlaybackInfo {\n const info: PlaybackInfo = {\n ...super.getCommonPlaybackInfo(),\n size: this.player.getViewMode() === ViewMode.Fullscreen ? PlayerSize.Fullscreen : PlayerSize.Window,\n playerTech: this.getPlayerTech(),\n isLive: this.player.isLive(),\n videoDuration: normalizeVideoDuration(this.videoDuration),\n streamFormat: this.player.getStreamType(),\n videoWindowWidth: this.player.getContainer().offsetWidth,\n videoWindowHeight: this.player.getContainer().offsetHeight,\n isMuted: this.player.isMuted(),\n isCasting: this.player.isCasting(),\n audioLanguage: isNotNullish(this.player.getAudio()) ? this.player.getAudio()?.lang : undefined,\n subtitleEnabled: false,\n droppedFrames: isNotNullish(this.player.getSource()) ? this.player.getDroppedVideoFrames() : 0,\n };\n\n this.applySubtitleProperties(info);\n this.applyPlaybackQualityProperties(info);\n this.applyCastingProperties(info);\n this.applySourceProperties(info);\n\n if (isNullish(info.streamFormat) || info.streamFormat === 'unknown') {\n // in case we cannot detect the streamFormat directly from\n // the player, we use the stored streamFormat as a fallback\n this.sourceInfoFallbackService.applyStreamFormat(info);\n }\n\n return info;\n }\n\n sourceChange(config: AnalyticsConfig) {\n this.stateMachine.callManualSourceChangeEvent(config, this.currentTime);\n }\n\n onError(): void {\n this.clearSegments();\n }\n\n private registerPlayerEventListeners() {\n this.player.on(this.player.exports.PlayerEvent.SourceUnloaded, (_event: any) => {\n this.segmentTracker.reset();\n this.eventCallback(Event.SOURCE_UNLOADED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SourceLoaded, (_event: any) => {\n this.videoCompletionTracker.reset();\n this.videoDuration = this.player.getDuration();\n this.videoCompletionTracker.setVideoDuration(this.player.getDuration());\n this.sourceInfoFallbackService.setStreamFormat(this.player.getStreamType());\n this.eventCallback(Event.SOURCE_LOADED, {});\n });\n\n this.player.on(this.player.exports.PlayerEvent.CastStarted, (event: any) => {\n this.eventCallback(Event.START_CAST, event);\n });\n\n this.player.on(this.player.exports.PlayerEvent.CastStopped, () => {\n this.eventCallback(Event.END_CAST, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Play, (e: UserInteractionEvent) => {\n if (e.issuer !== 'ui-seek') {\n this.eventCallback(Event.PLAY, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Playing, (e: UserInteractionEvent) => {\n if (e.issuer !== 'advertising-api') {\n this.eventCallback(Event.PLAYING, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Paused, (e: UserInteractionEvent) => {\n if (e.issuer !== 'ui-seek') {\n this.eventCallback(Event.PAUSE, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.TimeChanged, (_event: PlayerEventBase) => {\n if (!this.isAdPlaying) {\n this.lastTrackedCurrentTime = this.player.getCurrentTime();\n }\n this.eventCallback(Event.TIMECHANGED, {\n currentTime: this.lastTrackedCurrentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Seek, (e: UserInteractionEvent) => {\n if (this.allowSeeking(e)) {\n this.eventCallback(Event.SEEK, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Seeked, () => {\n this.eventCallback(Event.SEEKED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.StallStarted, () => {\n this.eventCallback(Event.START_BUFFERING, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.StallEnded, () => {\n this.eventCallback(Event.END_BUFFERING, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AudioPlaybackQualityChanged, (eventData) => {\n const audioQualityChangedData = eventData as AudioPlaybackQualityChangedEvent;\n const sourceQuality = audioQualityChangedData.sourceQuality;\n const targetQuality = audioQualityChangedData.targetQuality;\n\n if (isNullish(targetQuality)) {\n return;\n }\n\n // we don't want to track the initial audioQualityChange event thus, we only\n // track the event if the sourceQuality is not null\n if (isNullish(sourceQuality)) {\n this.qualityChangeService.setAudioBitrate(targetQuality.bitrate);\n return;\n }\n\n if (this.qualityChangeService.shouldAllowAudioQualityChange(targetQuality.bitrate)) {\n this.eventCallback(Event.AUDIO_CHANGE, {\n bitrate: targetQuality.bitrate,\n currentTime: this.currentTime,\n codec: (targetQuality as any).codec,\n });\n }\n\n this.qualityChangeService.setAudioBitrate(targetQuality.bitrate);\n });\n\n this.player.on(this.player.exports.PlayerEvent.VideoPlaybackQualityChanged, (eventData) => {\n const videoQualityChangedData = eventData as VideoPlaybackQualityChangedEvent;\n const sourceQuality = videoQualityChangedData.sourceQuality;\n const targetQuality = videoQualityChangedData.targetQuality;\n\n // if targetQuality is null we just ignore the event\n // this is probably and outlier or the end of a session\n // where we don't want to track quality changes\n if (isNullish(targetQuality)) {\n return;\n }\n\n // we don't want to track the initial videoQualityChange event thus, we only\n // track the event if the sourceQuality is not null\n if (isNullish(sourceQuality)) {\n this.qualityChangeService.setVideoBitrate(targetQuality.bitrate);\n return;\n }\n\n if (this.qualityChangeService.shouldAllowVideoQualityChange(targetQuality.bitrate)) {\n this.eventCallback(Event.VIDEO_CHANGE, {\n width: targetQuality.width,\n height: targetQuality.height,\n bitrate: targetQuality.bitrate,\n currentTime: this.currentTime,\n codec: (targetQuality as any).codec,\n });\n }\n\n this.qualityChangeService.setVideoBitrate(targetQuality.bitrate);\n });\n\n this.player.on(this.player.exports.PlayerEvent.ViewModeChanged, (e: any) => {\n if (e.to === 'fullscreen') {\n this.eventCallback(Event.START_FULLSCREEN, {\n currentTime: this.currentTime,\n });\n } else if (e.from === 'fullscreen') {\n this.eventCallback(Event.END_FULLSCREEN, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdStarted, (_event: any) => {\n this.eventCallback(Event.START_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdFinished, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdSkipped, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdError, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Muted, () => {\n this.eventCallback(Event.MUTE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Unmuted, () => {\n this.eventCallback(Event.UN_MUTE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Error, (event: any) => {\n this.eventCallback(Event.ERROR, {\n code: event.code,\n message: event.name,\n legacyData: event.data,\n currentTime: this.currentTime,\n data: {\n additionalData: JSON.stringify(event.data),\n },\n });\n if (\n event.code === ErrorCode.BITMOVIN_PLAYER_LICENSING_ERROR.code ||\n event.code === ErrorCode.SETUP_MISSING_LICENSE_WHITELIST.code\n ) {\n this._onLicenseCallFailed.dispatch({});\n }\n this.ssaiService.sendAdEngagementErrorSample(event.code, event.name);\n });\n\n this.player.on(this.player.exports.PlayerEvent.PlaybackFinished, () => {\n this.eventCallback(Event.END, {currentTime: this.currentTime});\n });\n\n this.player.on(this.player.exports.PlayerEvent.DownloadFinished, (event: any) => {\n if (event.downloadType.indexOf('drm/license/') === 0) {\n this.drmPerformanceInfo = {\n drmType: event.downloadType.replace('drm/license/', ''),\n drmLoadTime: event.downloadTime * 1000,\n };\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.AudioChanged, (_event: any) => {\n this.eventCallback(Event.AUDIOTRACK_CHANGED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SubtitleEnabled, (_event: any) => {\n this.eventCallback(Event.SUBTITLE_CHANGE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SubtitleDisabled, (_event: any) => {\n this.eventCallback(Event.SUBTITLE_CHANGE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.LicenseValidated, (event: any) => {\n if (event.data.analytics && event.data.analytics.key !== undefined) {\n this._onLicenseKeyReceived.dispatch({licenseKey: event.data.analytics.key});\n } else {\n this._onLicenseCallFailed.dispatch({});\n }\n });\n }\n\n private registerUnloadEventListeners() {\n let handleCollectorUnload = () => {\n if (!this.onBeforeUnLoadEvent) {\n this.onBeforeUnLoadEvent = true;\n // we use here the last tracked video time as we cannot be sure if the player is still working at this place\n const currentTime = this.lastTrackedCurrentTime;\n this.eventCallback(Event.UNLOAD, {currentTime});\n }\n this.release();\n };\n handleCollectorUnload = handleCollectorUnload.bind(true);\n\n this.player.on(this.player.exports.PlayerEvent.Destroy, handleCollectorUnload);\n this.windowEventTracker.addEventListener('beforeunload', handleCollectorUnload);\n this.windowEventTracker.addEventListener('unload', handleCollectorUnload);\n }\n\n private applySourceProperties(info: PlaybackInfo) {\n const source = this.player.getSource();\n if (isNullish(source)) {\n return;\n }\n\n info.videoTitle = source.title;\n info.mpdUrl = source.dash;\n info.m3u8Url = source.hls;\n\n const progSourceInfo = getSourceInfoFromBitmovinSourceConfig(source.progressive, this.player);\n info.progUrl = progSourceInfo.progUrl;\n if (this.player.getStreamType() === 'progressive') {\n info.videoBitrate = progSourceInfo.progBitrate;\n }\n }\n\n private applySubtitleProperties(info: PlaybackInfo) {\n let enabledSubtitle;\n if (this.player.subtitles) {\n enabledSubtitle = this.player.subtitles.list().find((s) => s.enabled === true);\n }\n\n info.subtitleEnabled = isNotNullish(enabledSubtitle);\n info.subtitleLanguage = isNotNullish(enabledSubtitle) ? enabledSubtitle.lang : null;\n }\n\n private applyPlaybackQualityProperties(info: PlaybackInfo) {\n const videoQuality = this.player.getPlaybackVideoData();\n if (isNotNullish(videoQuality)) {\n info.videoBitrate = videoQuality.bitrate;\n info.videoPlaybackHeight = videoQuality.height;\n info.videoPlaybackWidth = videoQuality.width;\n info.videoCodec = (videoQuality as any).codec;\n }\n\n const audioQuality = this.player.getPlaybackAudioData();\n if (isNotNullish(audioQuality)) {\n info.audioBitrate = audioQuality.bitrate;\n info.audioCodec = (audioQuality as any).codec;\n }\n }\n\n private applyCastingProperties(info: PlaybackInfo) {\n const isCasting = this.player.isCasting() || this.player.isAirplayActive() || false;\n info.isCasting = isCasting;\n if (!isCasting) {\n return;\n }\n\n // AirPlay\n if (this.player.isAirplayActive()) {\n info.castTech = CastTech.AirPlay;\n return;\n }\n\n // Casting Tech from RemoteControlConfig\n const remoteControlConfig = this.player.getConfig().remotecontrol;\n if (isNullish(remoteControlConfig)) {\n return;\n }\n\n switch (remoteControlConfig.type) {\n case 'googlecast':\n info.castTech = CastTech.GoogleCast;\n break;\n case 'websocket':\n info.castTech = CastTech.WebSocket;\n break;\n }\n }\n\n // with this check we ignore seek events which are smaller than the Threshold\n // mainly to ignore keyboard triggered seeks\n private allowSeeking(e: UserInteractionEvent): boolean {\n const seekEvent = e as SeekEvent;\n const seekDifference = Math.abs(seekEvent.position - seekEvent.seekTarget);\n return seekDifference > AnalyticsSettings.ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD;\n }\n\n static create(player: PlayerAPI, opts?: AnalyticsStateMachineOptions): Bitmovin8InternalAdapter {\n const speedMeter = new SpeedMeterAdapter(player, new DownloadSpeedMeter()).getDownloadSpeedMeter();\n const segmentTracker = new SegmentTrackerAdapter(player, new SegmentTracker()).getSegmentTracker();\n const httpRequestTrackingAdapter = new HttpRequestTrackingAdapter(player);\n const videoCompletionTracker = new VideoCompletionTracker();\n const sourceInfoFallbackService = new SourceInfoFallbackService();\n return new Bitmovin8InternalAdapter(\n player,\n speedMeter,\n segmentTracker,\n videoCompletionTracker,\n httpRequestTrackingAdapter,\n sourceInfoFallbackService,\n opts,\n );\n }\n}\n","import Timespan from '../types/Timespan';\nimport {isNullish} from '../utils/Utils';\n\nenum TimespanOverlappingType {\n None,\n Overlapping,\n FirstContainedInSecond,\n SecondContainedInFirst,\n}\n\nexport default class VideoCompletionTracker {\n private watched: Timespan[] = [];\n private videoDuration: number | null = null;\n\n reset(): void {\n this.watched = [];\n }\n\n /**\n * sets video Duration\n * @param videoDuration in sec\n */\n setVideoDuration(videoDuration: number): void {\n this.videoDuration = videoDuration * 1000;\n }\n\n /**\n * Adds the watched timespan to the tracker\n * @param watched watched timespan you want to add to the tracker\n * @returns how much time(video parts which have not been seen yet) was added to the tracker\n */\n addWatched(watched: Timespan): number {\n if (isNullish(this.videoDuration)) {\n throw new Error('no video duration set for completion tracker');\n }\n\n this.watched.push(watched);\n const overlappingTimespan = this.mergeWatched(this.watched);\n return (this.getDuration(watched) - overlappingTimespan) / this.videoDuration;\n }\n\n /**\n * returns the relative value of how much the user watch the content of the video\n */\n getCompletionPercentage(): number {\n if (isNullish(this.videoDuration)) {\n throw new Error('no video duration set for completion tracker');\n }\n\n let watched = 0;\n for (const w of this.watched) {\n watched += this.getDuration(w);\n }\n return watched / this.videoDuration;\n }\n\n /**\n * Recursive Method to merge All Watched Blocks\n * @param watched\n *\n * @returns how much timespan was overlapping while merging the watchBlocks\n */\n private mergeWatched(watched: Timespan[]): number {\n for (let i = 0; i < watched.length; i++) {\n const time1 = watched[i];\n for (let k = i + 1; k < watched.length; k++) {\n const time2 = watched[k];\n let overlappingTimespan = 0;\n const overlapType = this.getOverlappingType(time1, time2);\n\n if (overlapType === TimespanOverlappingType.Overlapping) {\n this.mergeAndReplace(time1, i, time2, k);\n overlappingTimespan = this.getOverlappingTimespan(time1, time2);\n } else if (overlapType === TimespanOverlappingType.FirstContainedInSecond) {\n this.watched.splice(i, 1);\n overlappingTimespan = this.getDuration(time1);\n } else if (overlapType === TimespanOverlappingType.SecondContainedInFirst) {\n this.watched.splice(k, 1);\n overlappingTimespan = this.getDuration(time2);\n }\n if (overlapType !== TimespanOverlappingType.None) {\n return overlappingTimespan + this.mergeWatched(this.watched);\n }\n }\n }\n return 0;\n }\n\n private getOverlappingType(first: Timespan, second: Timespan): TimespanOverlappingType {\n if (\n (this.isMomentInTimespan(first.end, second) && first.start < second.start) ||\n (this.isMomentInTimespan(first.start, second) && first.end > second.end)\n ) {\n return TimespanOverlappingType.Overlapping;\n } else if (this.isMomentInTimespan(first.start, second) && this.isMomentInTimespan(first.end, second)) {\n return TimespanOverlappingType.FirstContainedInSecond;\n } else if (this.isMomentInTimespan(second.start, first) && this.isMomentInTimespan(second.end, first)) {\n return TimespanOverlappingType.SecondContainedInFirst;\n }\n return TimespanOverlappingType.None;\n }\n\n private isMomentInTimespan(moment: number, timespan: Timespan): boolean {\n return moment >= timespan.start && moment < timespan.end;\n }\n\n private mergeAndReplace(first: Timespan, firstIndex: number, second: Timespan, secondIndex: number): void {\n const end = first.end > second.end ? first.end : second.end;\n const start = first.start < second.start ? first.start : second.start;\n const newWatchedTimespan: Timespan = {start, end};\n this.watched.splice(firstIndex, 1, newWatchedTimespan);\n this.watched.splice(secondIndex, 1);\n }\n\n private getOverlappingTimespan(first: Timespan, second: Timespan): number {\n const end = first.end < second.end ? first.end : second.end;\n const start = first.start >= second.start ? first.start : second.start;\n return end - start;\n }\n\n private getDuration(watched: Timespan): number {\n return Math.abs(watched.end - watched.start);\n }\n}\n","import {logger} from '../utils/Logger';\n\nimport {Feature} from './Feature';\nimport {FeatureConfig} from './FeatureConfig';\n\nexport class FeatureManager<TConfigContainer> {\n private features: Array<Feature<TConfigContainer, FeatureConfig>> = [];\n\n registerFeatures(features: Array<Feature<TConfigContainer, FeatureConfig>>) {\n this.features = features;\n }\n\n unregisterFeatures() {\n this.features.forEach((feature) => feature.disable());\n this.features = [];\n }\n\n resetFeatures() {\n this.features.forEach((feature) => feature.reset());\n }\n\n configureFeatures(authenticated: boolean, featureConfigs?: TConfigContainer) {\n this.features = this.features.filter((feature) => {\n const config = feature.configure(authenticated, featureConfigs);\n if (!authenticated || config?.enabled !== true) {\n logger.log(`Disabling feature ${feature.constructor.name} as it isn't enabled according to license callback.`);\n feature.disable();\n return false;\n }\n return true;\n });\n this.features.forEach((feature) => feature.enabled());\n }\n}\n","import type {AdBreak, AdBreakConfig, AdConfig, AdManifestLoadedEvent, AdTagConfig} from 'bitmovin-player';\n\nimport * as Utils from '../utils/Utils';\n\nexport class AdBreakSample {\n adPosition?: string;\n adOffset?: string;\n adScheduleTime?: number;\n adReplaceContentDuration?: number;\n adPreloadOffset?: number;\n adTagPath?: string;\n adTagServer?: string;\n adTagType?: string;\n adTagUrl?: string;\n adIsPersistent?: boolean;\n adIdPlayer?: string;\n manifestDownloadTime?: number;\n errorCode?: number;\n errorData?: string;\n errorMessage?: string;\n adFallbackIndex = 0;\n\n constructor(adConfig?: AdConfig, adManifestLoadedEvent?: AdManifestLoadedEvent) {\n if (adManifestLoadedEvent) {\n this.manifestDownloadTime = Utils.calculateTime(adManifestLoadedEvent.downloadTiming.downloadTime);\n }\n\n if (adConfig) {\n this.adReplaceContentDuration = Utils.calculateTimeWithUndefined(adConfig.replaceContentDuration);\n this.adFallbackIndex = ((adConfig as any).currentFallbackIndex || -1) + 1;\n }\n\n const adBreakConfig = adConfig as AdBreakConfig;\n if (adBreakConfig) {\n if (adBreakConfig.position === 'pre' || adBreakConfig.position === 'post') {\n this.adPosition = adBreakConfig.position;\n } else {\n this.adPosition = 'mid';\n this.adOffset = adBreakConfig.position;\n }\n\n this.adPreloadOffset = Utils.calculateTimeWithUndefined(adBreakConfig.preloadOffset);\n }\n\n const adTagConfig = adConfig as AdTagConfig;\n if (adTagConfig) {\n this.adIsPersistent = adTagConfig.persistent;\n let tag = adTagConfig.tag;\n if (\n this.adFallbackIndex > 0 &&\n adTagConfig.fallbackTags &&\n adTagConfig.fallbackTags.length >= this.adFallbackIndex\n ) {\n tag = adTagConfig.fallbackTags[this.adFallbackIndex - 1];\n }\n if (tag) {\n this.adTagType = tag.type;\n this.adTagUrl = tag.url;\n }\n if (this.adTagUrl) {\n const adTagDetails = Utils.getHostnameAndPathFromUrl(this.adTagUrl);\n this.adTagServer = adTagDetails.hostname;\n this.adTagPath = adTagDetails.path;\n }\n }\n\n const adBreak = adConfig as AdBreak;\n if (adBreak) {\n this.adScheduleTime = Utils.calculateTimeWithUndefined(adBreak.scheduleTime);\n this.adIdPlayer = adBreak.id;\n }\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {SEQUENCE_NUMBER_LIMIT} from '../utils/Settings';\n\nimport {Backend} from './Backend';\n\n/**\n * The `SequenceNumberBackend` is a decorator class that increments a samples sequence number and filters out samples\n * where the `sequenceNumber` exceeds a specified threshold.\n *\n * If a sample's `sequenceNumber` surpasses the threshold, it is not forwarded to the next backend.\n * Otherwise, the sample is passed along to the next backend for further processing.\n *\n * @implements {Backend}\n */\nexport class SequenceNumberBackend implements Backend {\n nextBackend: Backend;\n sequenceNumber = 0;\n\n constructor(underlying: Backend) {\n this.nextBackend = underlying;\n }\n\n sendRequest(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendAdRequest(sample);\n }\n\n private updateSampleBeforeSending(sample: Sample) {\n sample.sequenceNumber = this.sequenceNumber++;\n }\n\n private isSequenceNumberAboveThreshold(sample: Sample): boolean {\n return (sample.sequenceNumber ?? 0) > SEQUENCE_NUMBER_LIMIT;\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport type {AnalyticsConfig, AnalyticsDebugConfig} from '../types/AnalyticsConfig';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\n\nimport {Backend} from './Backend';\n\n/**\n * The `DebuggingBackend` is responsible for printing debugging information\n * before forwarding the requests to the specified underlying backend.\n *\n * This allows for inspection of specific fields in the sample data before it is sent.\n * The fields can be specified through the {@link AnalyticsDebugConfig#fields}.\n *\n * @implements {Backend}\n * */\nexport class DebuggingBackend implements Backend {\n private underlying: Backend;\n private debugFields?: string[];\n\n constructor(config: AnalyticsConfig, underlying: Backend) {\n this.underlying = underlying;\n if (config.debug && (config.debug as AnalyticsDebugConfig).fields) {\n this.debugFields = (config.debug as AnalyticsDebugConfig).fields;\n }\n }\n\n sendRequest(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.underlying.sendAdRequest(sample);\n }\n\n private printFields(sample: Sample) {\n if (this.debugFields && this.debugFields.length) {\n const fields = {};\n this.debugFields.forEach((f) => (fields[f] = sample[f]));\n logger.table([fields]);\n }\n }\n}\n","import type {DownloadFinishedEvent, PlayerAPI, PlayerExports} from 'bitmovin-player';\n\nimport {EventDispatcher, Subscribable} from '../../../core/EventDispatcher';\nimport {OnDownloadFinishedEventObject} from '../../../features/httprequesttracking/OnDownloadFinishedEventObject';\nimport {calculateTimeWithUndefined, getCurrentTimestamp} from '../../../utils/Utils';\nimport {HttpRequestType} from '../bitmovin8PlayerTypes';\n\nexport class HttpRequestTrackingAdapter implements Subscribable<OnDownloadFinishedEventObject> {\n private eventDispatcher = new EventDispatcher<OnDownloadFinishedEventObject>();\n private playerExports: PlayerExports;\n\n constructor(player: PlayerAPI) {\n this.playerExports = player.exports;\n player.on(this.playerExports.PlayerEvent.DownloadFinished, (event) =>\n this.onDownloadFinished(event as DownloadFinishedEvent),\n );\n }\n\n subscribe(callback: (args: OnDownloadFinishedEventObject) => void): () => void {\n return this.eventDispatcher.subscribe(callback);\n }\n\n unsubscribe(callback: (args: OnDownloadFinishedEventObject) => void) {\n this.eventDispatcher.unsubscribe(callback);\n }\n\n private onDownloadFinished(event?: DownloadFinishedEvent) {\n this.eventDispatcher.dispatch({\n httpRequest: {\n downloadTime: calculateTimeWithUndefined(event?.downloadTime) ?? 0,\n httpStatus: event?.httpStatus ?? 0,\n success: event?.success ?? false,\n timestamp: getCurrentTimestamp(),\n url: event?.url,\n size: event?.size,\n timeToFirstByte: calculateTimeWithUndefined(event?.timeToFirstByte),\n type: this.mapHttpRequestType(event?.downloadType),\n },\n });\n }\n\n private mapHttpRequestType(downloadType?: string): HttpRequestType {\n // Map downloadType to the HttpRequestType values\n if (Object.values(HttpRequestType).includes(downloadType as HttpRequestType)) {\n return downloadType as HttpRequestType;\n }\n return HttpRequestType.UNKNOWN;\n }\n}\n","import type {HeartbeatListener} from '../core/HeartbeatService';\nimport {HeartbeatService} from '../core/HeartbeatService';\nimport {SSAI_RELATED_SAMPLE_MARKER} from '../core/ssai/ssaiUtils';\nimport {ErrorCode} from '../enums/ErrorCode';\nimport {Event, EventMap} from '../enums/Event';\nimport type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport type {AnalyticsStateMachineOptions} from '../types/AnalyticsStateMachineOptions';\nimport type {AnalyticsEventBase} from '../types/EventData';\nimport type {NoExtraProperties} from '../types/NoExtraProperties';\nimport {HeartbeatPayload, StateMachineCallbacks} from '../types/StateMachineCallbacks';\nimport {logger} from '../utils/Logger';\nimport * as Settings from '../utils/Settings';\nimport * as Utils from '../utils/Utils';\nimport {isNotNullish} from '../utils/Utils';\n\nconst REBUFFERING_HEARTBEAT_INTERVALS = [3000, 5000, 10000, 30000, 59700];\n\nexport abstract class AnalyticsStateMachine implements HeartbeatListener {\n protected stateMachine: StateMachine.StateMachine & {[key: string]: any};\n protected onEnterStateTimestamp = 0;\n\n protected readonly videoStartupTimeoutMs: number = Settings.ANALYTICS_VIDEOSTART_TIMEOUT;\n protected readonly rebufferTimeoutMs: number = Settings.ANALYTICS_REBUFFER_TIMEOUT;\n protected readonly playingHeartbeatService: HeartbeatService;\n\n private rebufferingHeartbeatIntervalHandle?: number;\n private currentRebufferingIntervalIndex = 0;\n private rebufferingTimeoutHandle?: number;\n private videoStartTimeout?: number;\n\n constructor(\n protected stateMachineCallbacks: StateMachineCallbacks,\n playingHeartbeatService: HeartbeatService,\n opts: AnalyticsStateMachineOptions,\n ) {\n this.stateMachine = this.createStateMachine(opts);\n this.playingHeartbeatService = playingHeartbeatService;\n }\n\n abstract createStateMachine(opts: AnalyticsStateMachineOptions): StateMachine.StateMachine;\n\n /**\n * Sends out sample because of SSAI interaction\n *\n * @param timestamp current timestamp\n * @param eventObject contains player information\n */\n abstract onSsaiPlaybackInteraction(timestamp: number, eventObject: AnalyticsEventBase): void;\n\n callEvent<StateMachineEvent extends keyof EventMap, StateMachineEventData extends EventMap[StateMachineEvent]>(\n event: StateMachineEvent,\n eventData: NoExtraProperties<EventMap[StateMachineEvent], StateMachineEventData>,\n eventTimestamp: number,\n ): void {\n const stateMachineEventMethod = this.stateMachine[event];\n\n if (stateMachineEventMethod == null) {\n // If the event (aka. the event method) is not defined in the JSM, we log a warning,\n // because it means that we are explicitly trying to call that JSM event from our code (probably adapter),\n // but it was not defined in the JSM at all. Either we are missing it or it should not be called at all!\n logger.warn(`StateMachine ignored event \"${event}\" call, because it was not defined`, eventData, eventTimestamp);\n return;\n }\n\n try {\n // By default, if you try to call an event method not allowed in the current state, the state machine will throw an exception.\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n //\n // This JSM library behavior can be changed by providing \"a custom error handler\" in the `create()`\n // method of the state machine, and we do that in every state machine!\n //\n // But we still want to have here a try-catch block, in case of unexpected state machine code,\n // to avoid propagating the exception to the rest of the application (and breaking customer app).\n stateMachineEventMethod.call(this.stateMachine, eventTimestamp, eventData);\n } catch (e) {\n logger.error(\n `StateMachine ignored event \"${event}\" call, because it has thrown exception in the current state \"${this.currentState}\"`,\n eventData,\n eventTimestamp,\n e,\n );\n }\n }\n\n callManualSourceChangeEvent(analyticsConfig: AnalyticsConfig, playbackCurrentTimeInSeconds?: number) {\n this.callEvent(\n Event.MANUAL_SOURCE_CHANGE,\n {config: analyticsConfig, currentTime: playbackCurrentTimeInSeconds},\n Date.now(),\n );\n }\n\n get currentState(): string {\n return this.stateMachine.current;\n }\n\n resetIntervals() {\n this.clearVideoStartTimeout();\n this.clearRebufferingTimeoutHandle(true);\n this.clearRebufferingHeartbeatHandle();\n }\n\n //#region rebuffer timeout\n\n protected startRebufferingHeartbeatInterval(reset = true) {\n this.resetRebufferingHelpers(reset);\n\n this.startRebufferingTimeoutHandle();\n\n this.rebufferingHeartbeatIntervalHandle = window.setInterval(() => {\n const state = this.stateMachine.current.toLowerCase();\n if (state !== 'rebuffering') {\n this.resetRebufferingHelpers();\n return;\n }\n const timestamp = new Date().getTime();\n const stateDuration = timestamp - this.onEnterStateTimestamp;\n this.stateMachineCallbacks.heartbeat(stateDuration, state, {buffered: stateDuration});\n this.onEnterStateTimestamp = timestamp;\n this.currentRebufferingIntervalIndex = Math.min(\n this.currentRebufferingIntervalIndex + 1,\n REBUFFERING_HEARTBEAT_INTERVALS.length - 1,\n );\n this.startRebufferingHeartbeatInterval(false);\n }, REBUFFERING_HEARTBEAT_INTERVALS[this.currentRebufferingIntervalIndex]);\n }\n\n protected resetRebufferingHelpers(reset = true) {\n if (reset) {\n this.currentRebufferingIntervalIndex = 0;\n }\n this.clearRebufferingHeartbeatHandle();\n this.clearRebufferingTimeoutHandle(reset);\n }\n\n protected clearRebufferingHeartbeatHandle() {\n if (isNotNullish(this.rebufferingHeartbeatIntervalHandle)) {\n window.clearInterval(this.rebufferingHeartbeatIntervalHandle);\n this.rebufferingHeartbeatIntervalHandle = undefined;\n }\n }\n\n private startRebufferingTimeoutHandle() {\n if (this.currentRebufferingIntervalIndex > 0) {\n return;\n }\n this.rebufferingTimeoutHandle = window.setTimeout(() => {\n this.callEvent(\n Event.ERROR,\n {\n ...ErrorCode.BUFFERING_TIMEOUT_REACHED,\n data: {\n additionalData: `StateMachine timed out after ${this.rebufferTimeoutMs} ms of consecutive buffering.`,\n },\n },\n Utils.getCurrentTimestamp(),\n );\n this.stateMachineCallbacks.release();\n }, this.rebufferTimeoutMs);\n }\n\n protected clearRebufferingTimeoutHandle(reset: boolean) {\n if (reset && isNotNullish(this.rebufferingTimeoutHandle)) {\n window.clearTimeout(this.rebufferingTimeoutHandle);\n this.rebufferingTimeoutHandle = undefined;\n }\n }\n //#endregion\n\n //#region videoStartupFailed\n protected setVideoStartTimeout() {\n if (isNotNullish(this.videoStartTimeout)) {\n this.clearVideoStartTimeout();\n }\n this.videoStartTimeout = window.setTimeout(() => {\n this.callEvent(Event.VIDEOSTART_TIMEOUT, {}, Date.now());\n this.stateMachineCallbacks.release();\n }, this.videoStartupTimeoutMs);\n }\n\n protected clearVideoStartTimeout() {\n window.clearTimeout(this.videoStartTimeout);\n this.videoStartTimeout = undefined;\n }\n //#endregion\n\n onHeartbeat(eventObject: AnalyticsEventBase): void {\n this.sendPlayingSample(Date.now(), eventObject);\n }\n\n /**\n * Should be used in \"playing\" state only, and only by \"SSAI\" and \"Playing Heartbeat\" features,\n * otherwise it will log a warning and do nothing!\n *\n * Uses timestamp and eventObject.currentTime to reset time measurements and calls the\n * {@link StateMachineCallbacks.heartbeat} to send out a playing sample.\n *\n * We have chose to use {@link StateMachineCallbacks.heartbeat} callback here, because it was\n * the easiest and the fastest way to trigger 'playing' sample sending, without changing and\n * refactoring too much code, in future this code should be refactored with better naming.\n *\n * @param timestamp current timestamp\n * @param eventObject contains player information\n * @param triggeredBySsai boolean to mark the sample as SSAI triggered\n */\n protected sendPlayingSample(timestamp: number, eventObject: AnalyticsEventBase, triggeredBySsai = false) {\n const state = this.stateMachine.current.toLowerCase();\n if (state !== 'playing') {\n // our logic for \"SSAI\" and \"playing heartbeat\" is built on the assumption that we send only 'playing' samples,\n // but that \"if\" restriction is spread across the codebase, so we need to log a warning here, to see a potential\n // problems in our logic, if reported by from customer and report will contain these logs\n logger.warn(`Unexpected call of \"sendPlayingSample\" in AnalyticsStateMachine from \"${state}\" state`);\n return;\n }\n\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventObject);\n\n const stateDuration = timestamp - this.onEnterStateTimestamp;\n const payload: HeartbeatPayload = {played: stateDuration};\n\n if (triggeredBySsai) {\n payload[SSAI_RELATED_SAMPLE_MARKER] = true;\n }\n\n this.stateMachineCallbacks.heartbeat(stateDuration, state, payload);\n\n this.onEnterStateTimestamp = timestamp;\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventObject);\n }\n}\n","import {CollectorConfig} from '../../types/AnalyticsConfig';\nimport {post} from '../../utils/Http';\nimport {ANALYTICS_BACKEND_BASE_URL} from '../../utils/Settings';\nimport {isNotNullish, joinUrls} from '../../utils/Utils';\nimport {HttpRequest} from '../httprequesttracking/HttpRequest';\n\nimport {ErrorData} from './ErrorData';\nimport {ErrorDetail} from './ErrorDetail';\n\nexport class ErrorDetailBackend {\n get queue(): ReadonlyArray<ErrorDetail> {\n return this._queue;\n }\n\n get enabled(): boolean {\n return this._enabled;\n }\n\n set enabled(value: boolean) {\n this._enabled = value;\n }\n\n static copyErrorDetailTruncateStringsAndUrls(\n errorDetail: ErrorDetail,\n maxStringLength: number,\n maxUrlLength: number,\n ): ErrorDetail {\n return {\n ...errorDetail,\n message: errorDetail.message?.substr(0, maxStringLength),\n data: this.copyErrorDataTruncateStrings(errorDetail.data, maxStringLength),\n httpRequests: errorDetail.httpRequests?.map((request) => this.copyHttpRequestTruncateUrls(request, maxUrlLength)),\n };\n }\n\n static copyHttpRequestTruncateUrls(httpRequest: HttpRequest, maxLength: number): HttpRequest {\n return {\n ...httpRequest,\n url: httpRequest.url?.substr(0, maxLength),\n lastRedirectLocation: httpRequest.lastRedirectLocation?.substr(0, maxLength),\n };\n }\n\n static copyErrorDataTruncateStrings(errorData: ErrorData, maxStringLength: number): ErrorData {\n return {\n ...errorData,\n exceptionMessage: errorData.exceptionMessage?.substr(0, maxStringLength),\n additionalData: errorData.additionalData?.substr(0, maxStringLength),\n };\n }\n\n static copyErrorDetailTruncateHttpRequests(errorDetail: ErrorDetail, maxRequests: number): ErrorDetail {\n return {\n ...errorDetail,\n httpRequests: errorDetail.httpRequests?.slice(-maxRequests),\n };\n }\n\n // We use these as upper limits to avoid clients bombing us with data, actual truncation to documented limits is\n // happening in ingress\n private static MAX_URL_LENGTH = 450;\n private static MAX_STRING_LENGTH = 400;\n\n private readonly backendUrl: string;\n private readonly _queue: ErrorDetail[] = [];\n private _enabled = false;\n\n constructor(collectorConfig: CollectorConfig | undefined) {\n this.backendUrl = joinUrls(collectorConfig?.backendUrl ?? ANALYTICS_BACKEND_BASE_URL, '/analytics/error');\n }\n\n limitHttpRequestsOfQueuedErrorDetails(max: number) {\n this._queue.forEach((value, index) => {\n this._queue[index] = ErrorDetailBackend.copyErrorDetailTruncateHttpRequests(value, max);\n });\n }\n\n send(errorDetail: ErrorDetail) {\n const errorDetailCopy = ErrorDetailBackend.copyErrorDetailTruncateStringsAndUrls(\n errorDetail,\n ErrorDetailBackend.MAX_STRING_LENGTH,\n ErrorDetailBackend.MAX_URL_LENGTH,\n );\n if (this.enabled) {\n post(this.backendUrl, errorDetailCopy, () => undefined);\n } else {\n this._queue.push(errorDetailCopy);\n }\n }\n\n flush() {\n const copy = [...this._queue];\n let element = copy.shift();\n while (isNotNullish(element)) {\n this.removeFromQueue(element);\n this.send(element);\n element = copy.shift();\n }\n }\n\n clear() {\n this._queue.splice(0, this._queue.length);\n }\n\n private removeFromQueue(element: ErrorDetail) {\n const index = this._queue.findIndex((value) => value === element);\n if (index >= 0) {\n this._queue.splice(index, 1);\n }\n }\n}\n","import {Subscribable} from '../../core/EventDispatcher';\nimport {logger} from '../../utils/Logger';\nimport {Queue} from '../../utils/Queue';\n\nimport {HttpRequest} from './HttpRequest';\nimport {OnDownloadFinishedEventObject} from './OnDownloadFinishedEventObject';\n\nexport class HttpRequestTracking {\n private static DEFAULT_MAX_REQUESTS = 10;\n private _maxRequests: number = HttpRequestTracking.DEFAULT_MAX_REQUESTS;\n private _httpRequestQueue = new Queue<HttpRequest>();\n\n get maxRequests(): number {\n return this._maxRequests;\n }\n\n get httpRequests(): ReadonlyArray<HttpRequest> {\n return this._httpRequestQueue.items;\n }\n\n constructor(private subscribables: Array<Subscribable<OnDownloadFinishedEventObject>>) {\n subscribables.forEach((subscribable) => subscribable.subscribe(this.onDownloadFinishedHandler));\n }\n\n configure(maxRequests: number) {\n this._maxRequests = maxRequests;\n this._httpRequestQueue.limit(maxRequests);\n }\n\n disable() {\n this.subscribables.forEach((subscribable) => subscribable.unsubscribe(this.onDownloadFinishedHandler));\n this._httpRequestQueue.clear();\n }\n\n reset() {\n this._httpRequestQueue.clear();\n }\n\n private onDownloadFinishedHandler = (event: OnDownloadFinishedEventObject) => {\n try {\n this.addRequest(event.httpRequest);\n } catch (error) {\n logger.error(`HttpRequestTracking.onDownloadFinished: Error in handler`, error);\n }\n };\n\n private addRequest(httpRequest: HttpRequest) {\n this._httpRequestQueue.offer(httpRequest);\n this._httpRequestQueue.limit(this._maxRequests);\n }\n}\n","import type {SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\nimport {customDataValuesKeys} from '../../types/CustomDataValues';\nimport type {AdSample, Sample} from '../../types/Sample';\nimport {isNotNullish, isNullish} from '../../utils/Utils';\n\nimport type {\n InternalSsaiMetadata,\n SsaiEngagementErrorData,\n SsaiEngagementQuartileData,\n SsaiEngagementStartedData,\n} from './ssaiEngagementInteractionData';\n\n/**\n * Ssai marker property for {@link Sample} to indicate that this is \"ssai related sample\" and can cause the spike\n * on ingress side. It will be picked up in `AnalyticsCall` and used to send that \"ssai related sample\" as request\n * with ssai redirection. @see {@link ROUTING_URL_PARAM}\n *\n * What is \"ssai related sample\" ?\n * - \"last sample\" that was triggered to be sent, because of coming SSAI interaction, the SSAI ad break start (WITHOUT `sample.ad = 2`),\n * because it causes also the spike as all viewers are received same SSAI at the same time.\n * - all following samples, triggered by SSAI interaction while SSAI ad break is running (now WITH `sample.ad = 2`)\n *\n * We don't we need it with {@link AdSample} too?\n * Because all \"ssai related ad samples\" are triggered only during ssai ad break, so all have already\n * {@link AdSample#adType} property set and we can relay on that in `AnalyticsCall` to send them with ssai redirection.\n */\nexport const SSAI_RELATED_SAMPLE_MARKER = 'triggeredBySsai';\n\nexport function isSsaiRelatedSample(sample: AdSample | Sample): boolean {\n if (sample[SSAI_RELATED_SAMPLE_MARKER]) {\n delete sample[SSAI_RELATED_SAMPLE_MARKER]; // clean up the marker property that should not be present on the sample property\n return true;\n } else if ((sample as AdSample).adType === 2) {\n return true;\n }\n\n return false;\n}\n\n/**\n * Due to ssai being spiky by design, we should mark all analytics requests (with samples / ad samples)\n * that are ssai related, with a specific URL parameter. The load balancer can then route traffic according to the URL\n * parameter to a different ingress instance, which gives us more flexibility when ssai spikes are coming in.\n */\nexport const ROUTING_URL_PARAM = 'routingParam';\nexport const ROUTING_URL_PARAM_VALUE_SSAI = 'ssai';\n\nexport function appendSsaiRoutingParam(url: string): string {\n return `${url}?${ROUTING_URL_PARAM}=${ROUTING_URL_PARAM_VALUE_SSAI}`;\n}\n\nfunction createAdSampleFromSample(sample: Sample): AdSample {\n return {\n audioBitrate: sample?.audioBitrate,\n analyticsVersion: sample?.analyticsVersion,\n adPlaybackHeight: sample?.videoPlaybackHeight,\n adPlaybackWidth: sample?.videoPlaybackWidth,\n cdnProvider: sample?.cdnProvider,\n customData1: sample?.customData1,\n customData2: sample?.customData2,\n customData3: sample?.customData3,\n customData4: sample?.customData4,\n customData5: sample?.customData5,\n customData6: sample?.customData6,\n customData7: sample?.customData7,\n customData8: sample?.customData8,\n customData9: sample?.customData9,\n customData10: sample?.customData10,\n customData11: sample?.customData11,\n customData12: sample?.customData12,\n customData13: sample?.customData13,\n customData14: sample?.customData14,\n customData15: sample?.customData15,\n customData16: sample?.customData16,\n customData17: sample?.customData17,\n customData18: sample?.customData18,\n customData19: sample?.customData19,\n customData20: sample?.customData20,\n customData21: sample?.customData21,\n customData22: sample?.customData22,\n customData23: sample?.customData23,\n customData24: sample?.customData24,\n customData25: sample?.customData25,\n customData26: sample?.customData26,\n customData27: sample?.customData27,\n customData28: sample?.customData28,\n customData29: sample?.customData29,\n customData30: sample?.customData30,\n customData31: sample?.customData31,\n customData32: sample?.customData32,\n customData33: sample?.customData33,\n customData34: sample?.customData34,\n customData35: sample?.customData35,\n customData36: sample?.customData36,\n customData37: sample?.customData37,\n customData38: sample?.customData38,\n customData39: sample?.customData39,\n customData40: sample?.customData40,\n customData41: sample?.customData41,\n customData42: sample?.customData42,\n customData43: sample?.customData43,\n customData44: sample?.customData44,\n customData45: sample?.customData45,\n customData46: sample?.customData46,\n customData47: sample?.customData47,\n customData48: sample?.customData48,\n customData49: sample?.customData49,\n customData50: sample?.customData50,\n customUserId: sample?.customUserId,\n domain: sample?.domain,\n experimentName: sample?.experimentName,\n key: sample?.key,\n language: sample?.language,\n path: sample?.path,\n platform: sample?.platform,\n player: sample?.player,\n playerKey: sample?.playerKey,\n playerTech: sample?.playerTech,\n size: sample?.size,\n screenHeight: sample?.screenHeight,\n screenWidth: sample?.screenWidth,\n streamFormat: sample?.streamFormat,\n userAgent: sample?.userAgent,\n userId: sample?.userId,\n version: sample?.version,\n videoBitrate: sample?.videoBitrate,\n videoId: sample?.videoId,\n videoImpressionId: sample?.impressionId,\n videoTitle: sample?.videoTitle,\n videoWindowHeight: sample?.videoWindowHeight,\n videoWindowWidth: sample?.videoWindowWidth,\n };\n}\n\nexport function createErrorAdSample(\n playbackSample: Sample,\n ssaiEngagementErrorData: SsaiEngagementErrorData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementErrorData.currentAdImpressionId,\n adIndex: ssaiEngagementErrorData.adIndex,\n currentAdMetadata: ssaiEngagementErrorData.currentAdMetadata,\n quartile: undefined,\n quartileMetadata: undefined,\n errorCode: ssaiEngagementErrorData.errorCode,\n errorMessage: ssaiEngagementErrorData.errorMessage,\n timeSinceAdStartedInMs: ssaiEngagementErrorData.timeSinceAdStartedInMs,\n });\n}\n\nexport function createStartedAdSample(\n playbackSample: Sample,\n ssaiEngagementStartedData: SsaiEngagementStartedData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementStartedData.currentAdImpressionId,\n adIndex: ssaiEngagementStartedData.adIndex,\n currentAdMetadata: ssaiEngagementStartedData.currentAdMetadata,\n quartile: 'started',\n quartileMetadata: undefined,\n errorCode: undefined,\n errorMessage: undefined,\n timeSinceAdStartedInMs: undefined,\n });\n}\n\nexport function createQuartileAdSample(\n playbackSample: Sample,\n ssaiEngagementQuartileData: SsaiEngagementQuartileData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementQuartileData.currentAdImpressionId,\n adIndex: ssaiEngagementQuartileData.adIndex,\n currentAdMetadata: ssaiEngagementQuartileData.currentAdMetadata,\n quartile: ssaiEngagementQuartileData.quartile,\n quartileMetadata: ssaiEngagementQuartileData.quartileMetadata,\n timeSinceAdStartedInMs: ssaiEngagementQuartileData.timeSinceAdStartedInMs,\n errorCode: undefined,\n errorMessage: undefined,\n });\n}\n\nfunction buildAdSample({\n playbackSample,\n currentAdImpressionId,\n adIndex,\n currentAdMetadata,\n quartile,\n quartileMetadata,\n errorCode,\n errorMessage,\n timeSinceAdStartedInMs,\n}: {\n adIndex: number;\n currentAdImpressionId: string;\n currentAdMetadata: InternalSsaiMetadata;\n errorCode: number | undefined;\n errorMessage: string | undefined;\n playbackSample: Sample;\n quartile: 'started' | SsaiAdQuartile | undefined;\n quartileMetadata: SsaiAdQuartileMetadata | undefined;\n timeSinceAdStartedInMs: number | undefined;\n}): AdSample {\n const adEngagementSample: AdSample = {\n ...createAdSampleFromSample(playbackSample),\n adId: currentAdMetadata?.adId,\n adImpressionId: currentAdImpressionId,\n adIndex: adIndex,\n adPosition: currentAdMetadata?.adPosition,\n adSystem: currentAdMetadata?.adSystem,\n adType: 2,\n errorCode: errorCode,\n errorMessage: errorMessage,\n time: Date.now(),\n timeSinceAdStartedInMs: timeSinceAdStartedInMs,\n };\n\n // set quartile data\n switch (quartile) {\n case 'started':\n adEngagementSample.started = 1;\n break;\n case 'first':\n adEngagementSample.quartile1 = 1;\n adEngagementSample.quartile1FailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'midpoint':\n adEngagementSample.midpoint = 1;\n adEngagementSample.midpointFailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'third':\n adEngagementSample.quartile3 = 1;\n adEngagementSample.quartile3FailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'completed':\n adEngagementSample.completed = 1;\n adEngagementSample.completedFailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n }\n\n // set ssai customData\n const customData = currentAdMetadata?.customData;\n if (isNotNullish(customData)) {\n customDataValuesKeys.forEach((key) => {\n if (customData[key]) {\n adEngagementSample[key] = customData[key];\n }\n });\n }\n\n return adEngagementSample;\n}\n\n/**\n * Returns the current timestamp in milliseconds using the `performance.now()` method if available\n * to ensure monotonic timestamps; otherwise, it falls back to using `Date.now()`.\n *\n * Date.now() is dependent on the system clock and not monotonic, it may have been impacted by system\n * and user clock adjustments. The performance.now() method is relative to the timeOrigin property\n * which is a monotonic clock: its current time never decreases and isn't subject to adjustments.\n */\nexport function getCurrentMonotonicTimestampInMs(): number {\n if (isNullish(window.performance?.now) || typeof window.performance.now !== 'function') {\n return Date.now();\n }\n\n // floor to return integer value (not double as performance.now() returns)\n return Math.floor(performance.now());\n}\n\nexport function getMonotonicTimestampInMsSince(timestampInMs: number | undefined): number | undefined {\n if (isNullish(timestampInMs)) {\n return undefined;\n }\n\n return getCurrentMonotonicTimestampInMs() - timestampInMs;\n}\n","import {\n StateMachineErrorCallback,\n Error as StateMachineErrorCode,\n StateMachineEventDef,\n} from 'javascript-state-machine';\n\nimport {logger, padRight} from '../utils/Logger';\nimport {isNotNullish, isNullish} from '../utils/Utils';\n\n/**\n * @deprecated use {@link whileIn} instead, to switch mindset and think about allowed events in the current state\n * instead of thinking of current event and its allowed states. Because as analytics we focus mostly on reporting\n * states or states changes.\n */\nexport const on = (event: string): {stayIn: (state: string) => StateMachineEventDef} => ({\n stayIn: (state: string) => ({name: event, from: state, to: state}),\n});\n\ntype EventsToStateMachineEventDefFn = (...events: string[]) => StateMachineEventDef[];\ntype WhileInReturnType = {\n /**\n * Create {@link StateMachineEventDef} from event(s) to be used in the state machine definition, but ONLY to indicate\n * that we want to only pass event(s) over, to avoid a log message of ignored event in the current state from\n * the state machine.\n *\n * @remarks\n *\n * If we decide in the future to ignore {@link StateMachineErrorCode.INVALID_TRANSITION} logs created in\n * {@link customStateMachineErrorCallback}, this method and JSM event definitions created with could be removed\n * from source code. Until then, we use it to make code more readable.\n */\n passOver: EventsToStateMachineEventDefFn;\n\n /**\n * Same as {@link passOver}, but used in rare cases, when it indicates that we expect the event(s) to occur\n * in the current state, aka. we want to trigger the state machine event callbacks for these event(s),\n * even if we stay in the same state.\n *\n * @remarks\n *\n * If we don't expect the event while staying in the current state, we don't expect state machine event callbacks\n * to run, we should use {@link passOver} instead!\n */\n runEventCallbacksFor: EventsToStateMachineEventDefFn;\n};\n\n/**\n * This utility is here to help us write more readable code and let us define allowed/expected events in the current state.\n *\n * ### Example:\n *\n * Instead of writing:\n *\n * ```typescript\n * {name: Event.PAUSE, from: State.END, to: State.END},\n * {name: Event.SEEK, from: State.END, to: State.END},\n * {name: Event.SEEKED, from: State.END, to: State.END},\n * {name: Event.TIMECHANGED, from: State.END, to: State.END},\n * ```\n *\n * we can write:\n *\n * ```typescript\n * ...whileIn(State.END).passOver(Event.PAUSE, Event.SEEK, Event.SEEKED, Event.TIMECHANGED),\n * // OR when we expect and react on that event occurrence:\n * ...whileIn(State.END).runEventCallbacksFor(Event.PAUSE, Event.SEEK, Event.SEEKED, Event.TIMECHANGED),\n * ```\n *\n * @see customStateMachineErrorCallback\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n */\nexport const whileIn = (state: string): WhileInReturnType => {\n const stateMachineEventDefBuilderFn = (...events: string[]) =>\n events.map((event) => ({name: event, from: state, to: state}));\n return {runEventCallbacksFor: stateMachineEventDefBuilderFn, passOver: stateMachineEventDefBuilderFn};\n};\n\n/**\n * By default, if you try to call an event method not allowed in the current state,\n * the state machine will throw an exception (not allow it).\n *\n * This JSM library behavior can be changed by providing \"a custom error handler\" in the `create()`\n * method of the state machine, and we do that in every state machine!\n *\n * This way we make code more resilient to errors, because we do not throw errors from JSM event methods,\n * but instead we handle them here and just log them with {@link logger}.\n *\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n */\nexport const customStateMachineErrorCallback: StateMachineErrorCallback = (\n eventName,\n from,\n to,\n args,\n errorCode,\n errorMessage,\n _ex,\n) => {\n const loggerMessage = `StateMachine ignored event \"${eventName}\", ${errorMessage}`;\n const loggerMessageData = {\n eventName,\n from,\n to,\n args: isNotNullish(args) ? JSON.stringify(args) : undefined,\n errorCode,\n errorMessage,\n };\n\n // if caller tried to fire an event that was inappropriate in the current state\n if (errorCode === StateMachineErrorCode.INVALID_TRANSITION) {\n // The event itself is defined in JSM (in some other StateMachineEventDef). However, it is just not considered to\n // be appropriate in the current state.\n //\n // We should log it as a simple log. It is not an error nor a warning,\n // - because JSM will just stay in the same JSM state (and that can be considered as expected behavior)\n // - BUT it will NOT trigger JSM event callbacks like `onafterEVENT`, on `onbeforeEVENT`!\n logger.log(loggerMessage, loggerMessageData);\n return;\n }\n\n logger.error(loggerMessage, loggerMessageData);\n};\n\n/**\n * Log warning messages with {@link logger} about missing StateMachine callback,\n * if the state is not nullish and does not match any of the ignored states.\n */\nexport const logMissingCallbackWarning = (state: string | undefined, ignoreStates: string[] = []) => {\n if (isNullish(state)) {\n return;\n }\n\n const shouldReportMissingCallback = isNullish(ignoreStates.find((ignoredState) => state === ignoredState));\n if (shouldReportMissingCallback) {\n logger.warn('Could not find StateMachine callback function for ' + state);\n }\n};\n\n/** Log message with {@link logger} about StateMachine ENTER/LEAVE transition */\nexport const logStateMachineTransition = (\n transition: 'ENTER' | 'LEAVE',\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n) => {\n if (transition === 'ENTER') {\n logger.log(`[ENTER] ${padRight(to, 20)} EVENT: ${padRight(event, 20)} from ${padRight(from, 20)}`);\n } else {\n logger.log(`[LEAVE] ${padRight(from, 20)} EVENT: ${padRight(event, 20)} to ${padRight(to, 20)}`);\n }\n};\n","import type {AnalyticsConfig, CollectorConfig} from '../types/AnalyticsConfig';\nimport type {Sample} from '../types/Sample';\n\nimport {logger} from './Logger';\nimport {isBlank, isValidString} from './stringUtils';\nimport * as Utils from './Utils';\nimport {isNotNullish, isNullish} from './Utils';\n\n/**\n * Sanitize {@link AnalyticsConfig} to not be null/undefined\n *\n * Why we return the same config (same reference) passed to function as an argument?\n * Because in the past, we made a mistake and forget to prevent changing `AnalyticsConfig` vie kept reference\n * from outside. Now our customers are using this bug/feature, and we need to keep it for backward compatibility.\n * This should be fixed and changed in the future major release as part of `Collector API v3` changes.\n *\n * @returns A new empty config `{}`, if it was `null/undefined`, otherwise the same config (same reference).\n *\n */\nexport function sanitizeAnalyticsConfig(config: AnalyticsConfig | null | undefined): AnalyticsConfig {\n if (isNullish(config)) {\n return {};\n }\n\n if (!Utils.isBoolean(config.isLive)) {\n config.isLive = undefined;\n }\n\n return config;\n}\n\n/**\n * Log error with {@link logger}, if the new configuration is missing `title` property, but old configuration had one.\n */\nexport function guardConfigChangeAgainstMissingTitle(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig) {\n if (isNullish(oldConfig) || isNullish(newConfig)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (oldConfig.title && isBlank(newConfig.title)) {\n logger.error('The new analytics configuration does not contain the field `title`');\n }\n}\n\n/**\n * Log error with {@link logger}, if the new configuration is missing `isLive` property, but old configuration had one.\n */\nexport function guardConfigChangeAgainstMissingIsLive(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig) {\n if (isNullish(oldConfig) || isNullish(newConfig)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (oldConfig.isLive && isNullish(newConfig.isLive)) {\n logger.error(\n 'The new analytics configuration does not contain the field `isLive`. It will default to `false` which might be unintended? Once stream playback information is available the type will be populated.',\n );\n }\n}\n\n/**\n * Log warning with {@link logger}, if both `customUserId` and `userId` are set in the configuration.\n */\nexport function guardAgainstDuplicatedUserId(config: AnalyticsConfig) {\n if (isNullish(config)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (isNotNullish(config.customUserId) && isNotNullish(config.userId)) {\n logger.warn(\n 'Configuration Warning: \\n' +\n 'CustomUserId and UserId are set in the config \\n' +\n 'Value of UserId will be used in sample \\n' +\n 'Please only use one configuration field to set your userId',\n );\n }\n}\n\nexport function getDeviceInformationFromAnalyticsConfig(\n config: AnalyticsConfig,\n): Sample['deviceInformation'] | undefined {\n if (isNullish(config)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return undefined;\n }\n\n const deviceInformation: Sample['deviceInformation'] = {};\n\n if (isValidString(config.deviceType) && !isBlank(config.deviceType)) {\n // we are using `deviceInformation.model` field to pass `config.deviceType`, because of ingress\n // and how deviceInformation processing is implemented there.\n deviceInformation.model = config.deviceType;\n }\n\n if (isValidString(config.deviceClass) && !isBlank(config.deviceClass)) {\n deviceInformation.deviceClass = config.deviceClass;\n }\n\n if (Object.keys(deviceInformation).length === 0) {\n return undefined;\n }\n\n return deviceInformation;\n}\n\n/**\n * Get {@link CollectorConfig} `origin` field (if any), otherwise return sanitized hostname.\n */\nexport function getDomainFromAnalyticsConfig(config: AnalyticsConfig): string {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return config?.config?.origin ?? Utils.sanitizePath(window.location.hostname);\n}\n\nfunction removeSourceRelatedFields(config: AnalyticsConfig): AnalyticsConfig {\n const sourceSpecificProperties = ['cdnProvider', 'videoId', 'title', 'isLive', 'experimentName'];\n const customDataFieldsRegex = /customData\\d{1,2}$/g;\n\n for (const key in config) {\n if (isNotNullish(key.match(customDataFieldsRegex)) || sourceSpecificProperties.includes(key)) {\n delete config[key];\n }\n }\n\n return config;\n}\n\nfunction mergeCollectorConfig(\n oldCollectorConfig: CollectorConfig | undefined,\n newCollectorConfig: CollectorConfig | undefined,\n): CollectorConfig {\n if (isNotNullish(newCollectorConfig)) {\n // merging new config should enable the collector by default (unless explicitly disabled in the new config)\n return {...oldCollectorConfig, enabled: true, ...newCollectorConfig};\n }\n return oldCollectorConfig ?? {};\n}\n\nexport function mergeAnalyticsConfig(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig): AnalyticsConfig {\n const oldConfigWithoutSourceRelatedFields = removeSourceRelatedFields(oldConfig);\n const mergedCollectorConfig = mergeCollectorConfig(oldConfig.config, newConfig.config);\n\n return {\n ...oldConfigWithoutSourceRelatedFields,\n ...newConfig,\n config: mergedCollectorConfig,\n };\n}\n","import {isBlank, isValidString} from './stringUtils';\n\n// Declaration merging to extend the Window interface with WebOS API\n// see: https://webostv.developer.lge.com/develop/references/webostvjs-webos\ndeclare global {\n interface Window {\n /**\n * @deprecated In webOS TV 4.x or lower, only PalmSystem is supported, and in webOS TV 5.0 or higher,\n * both PalmSystem and webOSSystem are supported. Although PalmSystem is still supported for backward compatibility,\n * future support is not guaranteed so it is strongly recommended that you use webOSSystem in webOS TV 5.0 or higher.\n *\n * @see https://webostv.developer.lge.com/develop/guides/app-lifecycle-management\n */\n PalmSystem?: {\n deviceInfo?: string;\n };\n\n /**\n * Represents the current system interface that should be used on webOS TV 5.0 or higher.\n *\n * @see https://webostv.developer.lge.com/develop/references/webostvjs-webos\n */\n webOSSystem?: {\n /**\n * @see https://webostv.developer.lge.com/develop/references/webostvjs-webos#deviceinfo\n */\n deviceInfo?: string;\n };\n }\n}\n\ntype WebOSDeviceInfo = {modelName: string};\n\nexport function getWebOSTVModelName(): string | undefined {\n try {\n const info: WebOSDeviceInfo | undefined = window.webOSSystem?.deviceInfo\n ? JSON.parse(window.webOSSystem.deviceInfo)\n : window.PalmSystem?.deviceInfo && JSON.parse(window.PalmSystem.deviceInfo);\n if (isValidString(info?.modelName) && !isBlank(info?.modelName)) {\n return info.modelName;\n }\n return undefined;\n } catch {\n return undefined;\n }\n}\n\nexport function hasWindowWebOSApi(): boolean {\n return window.webOSSystem !== undefined || window.PalmSystem !== undefined;\n}\n","export enum PlayerSize {\n Fullscreen = 'FULLSCREEN',\n Window = 'WINDOW',\n}\n","import type {PlayerAPI} from 'bitmovin-player';\n\nimport {SegmentTracker} from '../../../core/SegmentTracker';\nimport {SegmentInfo} from '../../../types/SegmentInfo';\nimport * as Utils from '../../../utils/Utils';\n\ninterface DownloadFinishedEvent {\n attempt?: number;\n downloadType?: string;\n httpStatus: number;\n mimeType?: string;\n success: boolean;\n timestamp: number;\n type: string;\n url: string;\n}\n\ninterface SegmentPlaybackEvent {\n duration?: number;\n mediaInfo?: any;\n mimeType?: string;\n playbackTime?: number;\n representationId?: string;\n timestamp?: number;\n type?: string;\n uid?: string;\n url?: string;\n}\n\nexport class SegmentTrackerAdapter {\n private segmentTracker: SegmentTracker;\n\n constructor(player: PlayerAPI, segmentTracker: SegmentTracker) {\n this.segmentTracker = segmentTracker;\n\n player.on(player.exports.PlayerEvent.DownloadFinished, (event) => this.handleOnDownloadFinishEvent(event));\n player.on(player.exports.PlayerEvent.SegmentPlayback, (event) => this.handleSegmentPlaybackEvent(event));\n }\n\n getSegmentTracker(): SegmentTracker {\n return this.segmentTracker;\n }\n\n handleOnDownloadFinishEvent(event: any & DownloadFinishedEvent) {\n if (event.downloadType.indexOf('media/video') === 0) {\n const url = event.url;\n const segment: SegmentInfo = {\n name: Utils.getURLResourceName(url),\n url,\n timestamp: event.timestamp,\n };\n this.segmentTracker.addSegment(segment);\n }\n }\n\n handleSegmentPlaybackEvent = (event: any & SegmentPlaybackEvent) => {\n this.segmentTracker.removeSegment(event.url);\n };\n}\n","import type {\n Ad,\n AdBreak,\n AdBreakEvent,\n AdClickedEvent,\n AdEvent,\n AdManifestLoadedEvent,\n AdQuartileEvent,\n AdTagConfig,\n ErrorEvent,\n} from 'bitmovin-player';\n\nimport {AdModuleAPI} from '../adapters/internal/ads/AdModuleAPI';\nimport {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\nimport * as Utils from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\nimport {VERSION} from '../utils/Version';\nimport {ViewportTracker} from '../utils/ViewportTracker';\n\nimport {Analytics} from './Analytics';\n\nenum AdQuartile {\n FIRST_QUARTILE = 'firstQuartile',\n MIDPOINT = 'midpoint',\n THIRD_QUARTILE = 'thirdQuartile',\n}\n\nexport class AdAnalytics {\n static readonly MODULE_NAME = 'ads';\n private static readonly TIMEOUT_CURRENT_TIME_INTERVAL = 100;\n\n /** Boolean flag to prevent multiple calls of the {@link Event.UNLOAD} event */\n private onBeforeUnLoadEvent = false;\n private analytics: Analytics;\n private adapter: AdModuleAPI;\n private viewportTracker: ViewportTracker;\n\n private activeAdBreakSample?: AdBreakSample;\n private activeAdSample?: AdSample;\n\n private adManifestLoadedEvents: AdManifestLoadedEvent[] = [];\n private adStartupTimestamp?: number;\n private beginPlayingTimestamp?: number;\n private enterViewportTimestamp?: number;\n private isPlaying = false;\n private currentTime?: number;\n private currentTimeInterval?: number;\n private adPodPosition = 0;\n\n constructor(analytics: Analytics, adapter: AdModuleAPI) {\n this.analytics = analytics;\n this.adapter = adapter;\n\n this.adapter.adCallbacks.onAdStarted = (event) => this.onAdStarted(event);\n this.adapter.adCallbacks.onAdFinished = (event) => this.onAdFinished(event);\n this.adapter.adCallbacks.onAdBreakStarted = (event) => this.onAdBreakStarted(event);\n this.adapter.adCallbacks.onAdBreakFinished = (event) => this.onAdBreakFinished(event);\n this.adapter.adCallbacks.onAdClicked = (event) => this.onAdClicked(event);\n this.adapter.adCallbacks.onAdError = (event) => this.onAdError(event);\n this.adapter.adCallbacks.onAdManifestLoaded = (event) => this.onAdManifestLoaded(event);\n this.adapter.adCallbacks.onPlay = () => this.onPlay();\n this.adapter.adCallbacks.onPause = () => this.onPause();\n this.adapter.adCallbacks.onBeforeUnload = () => this.onBeforeUnload();\n this.adapter.adCallbacks.onAdSkipped = (event) => this.onAdSkipped(event);\n this.adapter.adCallbacks.onAdQuartile = (event) => this.onAdQuartile(event);\n\n this.viewportTracker = new ViewportTracker(this.adapter.getContainer(), () => this.onIntersectionChanged(), 0.5);\n }\n\n release() {\n this.clearCurrentTimeInterval();\n this.viewportTracker.dispose();\n }\n\n onIntersectionChanged() {\n if (!this.activeAdSample) {\n return;\n }\n if (this.isContainerInViewport()) {\n this.enterViewportTimestamp = Utils.getCurrentTimestamp();\n } else {\n if (this.enterViewportTimestamp) {\n this.activeAdSample.timeInViewport =\n (this.activeAdSample.timeInViewport || 0) + Utils.getCurrentTimestamp() - this.enterViewportTimestamp;\n }\n }\n }\n\n isContainerInViewport(): boolean {\n return this.viewportTracker ? this.viewportTracker.isInViewport() : true;\n }\n\n onPlay() {\n if (this.adapter && this.adapter.isLinearAdActive() && this.activeAdSample) {\n const timestamp = Utils.getCurrentTimestamp();\n this.beginPlayingTimestamp = timestamp;\n this.enterViewportTimestamp = timestamp;\n this.isPlaying = true;\n }\n }\n\n onPause() {\n if (this.adapter && this.adapter.isLinearAdActive() && this.activeAdSample) {\n this.updatePlayingTime(this.activeAdSample);\n this.isPlaying = false;\n }\n }\n\n onAdManifestLoaded(event: AdManifestLoadedEvent) {\n const adTagConfig = event.adConfig as AdTagConfig;\n if (adTagConfig && adTagConfig.tag && adTagConfig.tag.type === 'vmap') {\n this.sendAnalyticsRequest(new AdBreakSample(event.adConfig, event));\n } else if (event.adBreak) {\n this.adManifestLoadedEvents.push(event);\n }\n }\n\n onAdBreakStarted(event: AdBreakEvent) {\n this.adPodPosition = 0;\n this.activeAdBreakSample = new AdBreakSample(event.adBreak, this.getAdManifestLoadedEvent(event.adBreak));\n this.adStartupTimestamp = Utils.getCurrentTimestamp();\n }\n\n onAdBreakFinished(_event: AdBreakEvent) {\n this.resetActiveAd();\n this.activeAdBreakSample = undefined;\n }\n\n onAdStarted(event: AdEvent) {\n if (!event.ad.isLinear) {\n return;\n }\n\n this.resetActiveAd();\n this.activeAdSample = new AdSample(event.ad);\n this.currentTime = undefined;\n this.activeAdSample.adStartupTime = this.adStartupTimestamp\n ? Utils.getCurrentTimestamp() - this.adStartupTimestamp\n : undefined;\n\n this.startAd(this.activeAdSample);\n }\n\n onAdFinished(_event: AdEvent) {\n if (!this.activeAdBreakSample || !this.activeAdSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.completed = 1;\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.adDuration);\n }\n\n onAdSkipped(_event: AdEvent) {\n if (!this.activeAdBreakSample || !this.activeAdSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.skipped = 1;\n adSample.skipPosition = this.currentTime;\n adSample.skipPercentage = Utils.calculatePercentage(\n this.activeAdSample.skipPosition,\n this.activeAdSample.adDuration,\n );\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.skipPosition);\n }\n\n onAdError(event: ErrorEvent) {\n const {adConfig, adBreak, code, message} = event.data || {\n adBreak: undefined,\n adConfig: undefined,\n code: undefined,\n message: undefined,\n };\n\n const adBreakSample = new AdBreakSample(\n adBreak || adConfig,\n adBreak ? this.getAdManifestLoadedEvent(adBreak) : undefined,\n );\n\n adBreakSample.errorCode = code || event.code;\n adBreakSample.errorData = JSON.stringify(event.data);\n adBreakSample.errorMessage = message || event.name;\n\n let adSample;\n let errorPosition;\n if (\n this.activeAdSample &&\n adBreak &&\n adBreak.ads &&\n (adBreak.ads as any[]).includes((ad: Ad) => ad.id === (this.activeAdSample as AdSample).adId)\n ) {\n adSample = this.activeAdSample;\n errorPosition = adSample.errorPosition = this.currentTime;\n adSample.errorPercentage = Utils.calculatePercentage(adSample.errorPosition, adSample.adDuration);\n }\n this.completeAd(adBreakSample, adSample, errorPosition);\n }\n\n onAdClicked(event: AdClickedEvent) {\n if (!this.activeAdSample) {\n return;\n }\n this.activeAdSample.adClickthroughUrl = event.clickThroughUrl;\n this.activeAdSample.clicked = 1;\n this.activeAdSample.clickPosition = this.currentTime;\n this.activeAdSample.clickPercentage = Utils.calculatePercentage(\n this.activeAdSample.clickPosition,\n this.activeAdSample.adDuration,\n );\n }\n\n onAdQuartile(event: AdQuartileEvent) {\n if (!this.activeAdSample) {\n return;\n }\n if (event.quartile === AdQuartile.FIRST_QUARTILE) {\n this.activeAdSample.quartile1 = 1;\n } else if (event.quartile === AdQuartile.MIDPOINT) {\n this.activeAdSample.midpoint = 1;\n } else if (event.quartile === AdQuartile.THIRD_QUARTILE) {\n this.activeAdSample.quartile3 = 1;\n }\n }\n\n onBeforeUnload() {\n if (this.onBeforeUnLoadEvent) {\n return;\n }\n this.onBeforeUnLoadEvent = true;\n if (!this.activeAdSample || !this.activeAdBreakSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.closed = 1;\n adSample.closePosition = this.currentTime;\n adSample.closePercentage = Utils.calculatePercentage(adSample.closePosition, adSample.adDuration);\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.closePosition);\n }\n\n createNewAdAnalyticsSample(analyticsSample: Sample): AdAnalyticsSample {\n const moduleInfo = this.adapter.getAdModuleInfo();\n return {\n ...new AdAnalyticsSample(analyticsSample),\n analyticsVersion: VERSION,\n adModule: moduleInfo.name,\n adModuleVersion: moduleInfo.version,\n playerStartupTime: this.analytics.playerStartupTime,\n pageLoadTime: this.analytics.pageLoadTime,\n autoplay: this.analytics.autoplay,\n pageLoadType: Utils.getPageLoadType(),\n };\n }\n\n private getAdManifestLoadedEvent(adBreak: AdBreak) {\n if (!adBreak) {\n return undefined;\n }\n return this.adManifestLoadedEvents.find((i) => i.adBreak && i.adBreak.id === adBreak.id);\n }\n\n private sendAnalyticsRequest(adBreakSample: AdBreakSample, adSample?: AdSample) {\n const sample = {\n ...this.createNewAdAnalyticsSample(this.analytics.sample),\n ...adBreakSample,\n ...(adSample || new AdSample()),\n };\n sample.time = Utils.getCurrentTimestamp();\n sample.adImpressionId = generateUUID();\n sample.percentageInViewport = Utils.calculatePercentage(sample.timeInViewport, sample.timePlayed);\n this.analytics.backend.sendAdRequest(sample);\n }\n\n private updatePlayingTime(adSample: AdSample) {\n const timestamp = Utils.getCurrentTimestamp();\n if (this.beginPlayingTimestamp && this.isPlaying) {\n if (adSample.timePlayed !== undefined) {\n adSample.timePlayed += timestamp - this.beginPlayingTimestamp;\n }\n if (this.isContainerInViewport() && this.enterViewportTimestamp && adSample.timeInViewport !== undefined) {\n adSample.timeInViewport += timestamp - this.enterViewportTimestamp;\n }\n }\n }\n\n private startAd(adSample: AdSample) {\n adSample.started = 1;\n adSample.timePlayed = 0;\n adSample.timeInViewport = 0;\n adSample.adPodPosition = this.adPodPosition;\n const timestamp = Utils.getCurrentTimestamp();\n this.beginPlayingTimestamp = timestamp;\n this.enterViewportTimestamp = this.isContainerInViewport() ? timestamp : undefined;\n this.isPlaying = true;\n this.currentTime = 0;\n this.adPodPosition++;\n this.currentTimeInterval = window.setInterval(() => {\n try {\n if (\n adSample &&\n adSample.adDuration !== undefined &&\n adSample.adDuration > 0 &&\n this.adapter.isLinearAdActive()\n ) {\n this.currentTime = Utils.calculateTime(Math.max(this.adapter.currentTime(), 0));\n }\n } catch (e) {\n logger.log('AdStarted monitoring interval failed and got cleared', e);\n this.resetActiveAd();\n }\n }, AdAnalytics.TIMEOUT_CURRENT_TIME_INTERVAL);\n }\n\n private completeAd(adBreakSample: AdBreakSample, adSample: AdSample = new AdSample(), exitPosition?: number) {\n adSample.exitPosition = exitPosition;\n adSample.playPercentage = Utils.calculatePercentage(adSample.exitPosition, adSample.adDuration);\n\n // reset startupTimestamp for the next ad, in case there are multiple ads in one ad break\n this.adStartupTimestamp = Utils.getCurrentTimestamp();\n this.updatePlayingTime(adSample);\n this.isPlaying = false;\n this.sendAnalyticsRequest(adBreakSample, adSample);\n }\n\n private resetActiveAd() {\n this.clearCurrentTimeInterval();\n this.activeAdSample = undefined;\n }\n\n private clearCurrentTimeInterval() {\n window.clearInterval(this.currentTimeInterval);\n delete this.currentTime;\n }\n}\n","import {SsaiAdBreakMetadata, SsaiAdMetadata, SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\n\nexport type InternalSsaiMetadata = SsaiAdBreakMetadata & SsaiAdMetadata;\n\ntype SsaiEngagementBaseData = {\n adIndex: number;\n currentAdImpressionId: string;\n currentAdMetadata: InternalSsaiMetadata;\n type: 'error' | 'quartile' | 'started';\n};\n\nexport type SsaiEngagementErrorData = SsaiEngagementBaseData & {\n errorCode: number;\n errorMessage: string;\n timeSinceAdStartedInMs: number | undefined;\n type: 'error';\n};\n\nexport function isSsaiEngagementErrorData(data: SsaiEngagementInteractionData): data is SsaiEngagementErrorData {\n return data.type === 'error';\n}\n\nexport type SsaiEngagementQuartileData = SsaiEngagementBaseData & {\n quartile: SsaiAdQuartile;\n quartileMetadata: SsaiAdQuartileMetadata;\n timeSinceAdStartedInMs: number | undefined;\n type: 'quartile';\n};\n\nexport function isSsaiEngagementQuartileData(data: SsaiEngagementInteractionData): data is SsaiEngagementQuartileData {\n return data.type === 'quartile';\n}\n\nexport type SsaiEngagementStartedData = SsaiEngagementBaseData & {type: 'started'};\n\nexport function isSsaiEngagementStartedData(data: SsaiEngagementInteractionData): data is SsaiEngagementStartedData {\n return data.type === 'started';\n}\n\nexport type SsaiEngagementInteractionData =\n | SsaiEngagementErrorData\n | SsaiEngagementQuartileData\n | SsaiEngagementStartedData;\n","import {Subscribable} from '../../core/EventDispatcher';\nimport {CollectorConfig} from '../../types/AnalyticsConfig';\nimport {FeatureConfigContainer} from '../../types/FeatureConfigContainer';\nimport {logger} from '../../utils/Logger';\nimport {getCurrentTimestamp, isNullish} from '../../utils/Utils';\nimport {VERSION} from '../../utils/Version';\nimport {Feature} from '../Feature';\nimport {HttpRequestTracking} from '../httprequesttracking/HttpRequestTracking';\n\nimport {ErrorDetail} from './ErrorDetail';\nimport {ErrorDetailBackend} from './ErrorDetailBackend';\nimport {ErrorDetailTrackingConfig} from './ErrorDetailTrackingConfig';\nimport {OnErrorDetailEventObject} from './OnErrorDetailEventObject';\n\nexport interface ErrorDetailTrackingSettingsProvider {\n readonly licenseKey: string;\n readonly domain: string;\n readonly impressionId: string;\n readonly collectorConfig?: CollectorConfig;\n}\n\nexport class ErrorDetailTracking extends Feature<FeatureConfigContainer, ErrorDetailTrackingConfig> {\n private errorIndex = 0;\n\n constructor(\n private settingsProvider: ErrorDetailTrackingSettingsProvider,\n private backend: ErrorDetailBackend,\n private subscribables: Array<Subscribable<OnErrorDetailEventObject>>,\n private httpRequestTracking: HttpRequestTracking | undefined,\n ) {\n super();\n subscribables.forEach((subscribable) => subscribable.subscribe(this.onErrorHandler));\n }\n\n reset(): void {\n this.httpRequestTracking?.reset();\n this.errorIndex = 0;\n }\n\n enabled(): void {\n this.backend.enabled = true;\n this.backend.flush();\n }\n\n disabled(): void {\n this.errorIndex = 0;\n this.httpRequestTracking?.disable();\n this.backend.clear();\n this.subscribables.forEach((subscribable) => subscribable.unsubscribe(this.onErrorHandler));\n }\n\n configured(_authenticated: boolean, config?: ErrorDetailTrackingConfig): void {\n const maxRequests = Math.max(config?.numberOfHttpRequests ?? 0, 0);\n this.httpRequestTracking?.configure(maxRequests);\n this.backend.limitHttpRequestsOfQueuedErrorDetails(maxRequests);\n }\n\n extractConfig(configContainer: FeatureConfigContainer): ErrorDetailTrackingConfig | undefined {\n return configContainer.errorDetails;\n }\n\n private onErrorHandler = (event: OnErrorDetailEventObject) => {\n try {\n if (!this.isEnabled) {\n return;\n }\n\n const httpRequests = this.httpRequestTracking?.httpRequests;\n const httpRequestsCopy = isNullish(httpRequests) ? undefined : [...httpRequests];\n const errorIndex = this.errorIndex;\n this.errorIndex++;\n\n const errorDetail: ErrorDetail = {\n platform: 'web',\n licenseKey: this.settingsProvider.licenseKey,\n domain: this.settingsProvider.domain,\n impressionId: this.settingsProvider.impressionId,\n analyticsVersion: VERSION,\n errorId: errorIndex,\n timestamp: getCurrentTimestamp(),\n code: event.code,\n message: event.message,\n data: event.errorData ?? {\n additionalData: undefined,\n exceptionMessage: undefined,\n exceptionStacktrace: undefined,\n },\n httpRequests: httpRequestsCopy,\n };\n\n logger.log(`ErrorDetailTracking.onError: ${JSON.stringify(errorDetail)}`);\n this.backend.send(errorDetail);\n } catch (error) {\n logger.error(`ErrorDetailTracking.onError: Error in handler`, error);\n }\n };\n}\n","import {DownloadSpeedInfo} from '../types/DownloadSpeedInfo';\nimport {SpeedMeasurement} from '../types/SpeedMeasurement';\nimport {Converter} from '../utils/Converter';\n\nimport {Measure} from './Measure';\n\nexport class DownloadSpeedMeter {\n protected measures: Measure[];\n\n constructor() {\n this.measures = [];\n }\n\n reset(): void {\n this.measures = [];\n }\n\n addMeasurement(measurement: SpeedMeasurement): void {\n if (measurement.httpStatus >= 400) {\n return;\n }\n const measure = new Measure(measurement);\n\n const threshold = Converter.bitsToBytes(300 * 1000 * 1000); // 300 Megabit per second in bytes\n if (measure.speed >= threshold) {\n return;\n }\n\n this.measures.push(measure);\n }\n\n getInfo(): DownloadSpeedInfo {\n return {\n segmentsDownloadCount: this.measures.length,\n segmentsDownloadSize: this.measures.map((m) => m.size).reduce(this.add, 0),\n segmentsDownloadTime: Math.ceil(this.totalTime() * 1000),\n avgDownloadSpeed: this.avgSpeed(),\n minDownloadSpeed: this.minSpeed(),\n maxDownloadSpeed: this.maxSpeed(),\n avgTimeToFirstByte: this.avgTimeToFirstByte(),\n };\n }\n\n private add(a: number, b: number): number {\n return a + b;\n }\n\n private avgSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n const totalSpeed = this.speeds().reduce((a, b) => {\n return a + b;\n }, 0);\n const numMeasurements = this.measures.length;\n return this.bytePerSecondToBitPerSecond(totalSpeed / numMeasurements);\n }\n\n private bytePerSecondToBitPerSecond(bps: number): number {\n return Converter.bytesToBits(bps);\n }\n\n private minSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.bytePerSecondToBitPerSecond(Math.min(...this.speeds()));\n }\n\n private speeds(): number[] {\n return this.measures.map((m) => {\n return m.speed;\n });\n }\n\n private maxSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.bytePerSecondToBitPerSecond(Math.max(...this.speeds()));\n }\n\n private totalTime(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.measures.reduce((a, b) => {\n return a + b.duration;\n }, 0);\n }\n\n private avgTimeToFirstByte(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n const avg =\n this.measures.reduce((a, b) => {\n return a + b.timeToFirstByte * 1000;\n }, 0) / this.measures.length;\n\n return Math.ceil(avg);\n }\n}\n","import {ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD} from '../utils/Settings';\nimport * as Settings from '../utils/Settings';\nimport {isNotNullish} from '../utils/Utils';\n\nconst INITIAL_VALUE = 0;\n\nexport default class QualityChangeService {\n private qualityChangeCount = INITIAL_VALUE;\n private previousVideoBitrate = INITIAL_VALUE;\n private previousAudioBitrate = INITIAL_VALUE;\n private resetIntervalId?: number;\n private startupHasFinished = false;\n\n constructor(private qualityChangeThreshold: number = ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD) {}\n\n resetValues() {\n this.qualityChangeCount = INITIAL_VALUE;\n this.previousAudioBitrate = INITIAL_VALUE;\n this.previousVideoBitrate = INITIAL_VALUE;\n this.startupHasFinished = false;\n this.stopResetInterval();\n }\n\n isQualityChangeEventEnabled(): boolean {\n return this.qualityChangeCount <= this.qualityChangeThreshold;\n }\n\n increaseCounter() {\n this.qualityChangeCount++;\n }\n\n shouldAllowVideoQualityChange(newBitrate: number | undefined): boolean {\n return (\n this.startupHasFinished &&\n isNotNullish(newBitrate) &&\n !isNaN(newBitrate) &&\n this.previousVideoBitrate !== INITIAL_VALUE &&\n this.previousVideoBitrate !== newBitrate &&\n this.isQualityChangeEventEnabled()\n );\n }\n\n setVideoBitrate(newBitrate: number): void {\n // only bitrates after startup are relevant since some players\n // report initial bitrates before startup that differ from the\n // ones that are used after startup, which would lead to\n // wrong quality change events\n if (this.startupHasFinished) {\n this.previousVideoBitrate = newBitrate;\n }\n }\n\n setStartupHasFinished() {\n this.startupHasFinished = true;\n }\n\n shouldAllowAudioQualityChange(newBitrate: number | undefined): boolean {\n return (\n this.startupHasFinished &&\n isNotNullish(newBitrate) &&\n !isNaN(newBitrate) &&\n this.previousAudioBitrate !== INITIAL_VALUE &&\n this.previousAudioBitrate !== newBitrate &&\n this.isQualityChangeEventEnabled()\n );\n }\n\n setAudioBitrate(newBitrate: number): void {\n // only bitrates after startup are relevant since some players\n // report initial bitrates before startup that differ from the\n // ones that are used after startup, which would lead to\n // wrong quality change events\n if (this.startupHasFinished) {\n this.previousAudioBitrate = newBitrate;\n }\n }\n\n startResetInterval() {\n if (this.resetIntervalId !== undefined) {\n return;\n }\n\n this.resetIntervalId = window.setInterval(() => {\n this.resetCounter();\n }, Settings.ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL);\n }\n\n stopResetInterval() {\n if (this.resetIntervalId === undefined) {\n return;\n }\n\n window.clearInterval(this.resetIntervalId);\n delete this.resetIntervalId;\n }\n\n private resetCounter() {\n this.qualityChangeCount = 0;\n }\n}\n","/* eslint-disable perfectionist/sort-enums */\n\nexport enum PAGE_LOAD_TYPE {\n FOREGROUND = 1,\n BACKGROUND = 2,\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","import {Bitmovin8Adapter} from './adapters/bitmovin8/Bitmovin8Adapter';\nimport {PlayerModule} from './adapters/bitmovin8/playerModule';\nimport {CdnProvider} from './enums/CDNProvider';\nimport {Player} from './enums/Player';\nimport {VERSION} from './utils/Version';\n\nexport {VERSION as version};\n\nexport type {AnalyticsConfig} from './types/AnalyticsConfig';\n\nexport {Player as Players};\nexport {CdnProvider as CdnProviders};\n\nexport {Bitmovin8Adapter};\n\nexport const adapters = {\n Bitmovin8Adapter,\n};\n\nexport {PlayerModule};\n\nexport default {\n PlayerModule: PlayerModule,\n};\n"],"names":["root","factory","exports","module","define","amd","self","url","body","callback","async","xhttp","isLegacyXDomainRequestUsed","window","XDomainRequest","XMLHttpRequest","responseCallback","readyState","DONE","responseText","sampleResponse","JSON","parse","onload","onreadystatechange","open","setRequestHeader","send","stringify","e","logger","error","_config","undefined","_isEnabled","this","disable","disabled","configure","authenticated","configContainer","isNotNullish","extractConfig","configured","Feature","next","nextBackend","sendRequest","sample","isPlayedAboveThreshold","sendUnloadRequest","sendRequestSynchronous","sendAdRequest","isNullish","played","LongPlaytimeFilteringBackend","videoFormatCodecMap","avc","vp9","av1","hevc","Object","getOwnPropertyNames","filter","format","some","codec","isCodecSupported","MediaSource","isTypeSupported","CodecHelper","Player","player","meter","on","PlayerEvent","DownloadFinished","event","handleOnDownloadFinishEvent","getDownloadSpeedMeter","success","downloadType","indexOf","addMeasurement","duration","downloadTime","size","timeToFirstByte","timestamp","Date","httpStatus","SpeedMeterAdapter","callbacks","subscribe","push","unsubscribe","dispatch","args","slice","forEach","index","splice","length","EventDispatcher","PlayerModule","name","Analytics","Bitmovin8Adapter","hooks","setup","config","getConfig","isConfigMissing","isAnalyticsDisabled","analytics","Promise","resolve","analyticsModuleInstance","analyticsBitmovin8Adapter","COOKIE_NAME_BITMOVIN_ANALYTICS_UUID","COOKIE_DEFAULT_MAX_AGE","collectorConfig","cookiesEnabled","deleteCookie","userId","generateUUID","existingUserId","getCookie","isBlank","cookieDomain","validateCookieDomainValue","cookiesDomain","cookieMaxAge","validateCookieMaxAgeValue","cookiesMaxAge","nowMillis","now","cookieExpires","toUTCString","setCookie","domain","expires","maxAge","SessionPersistenceHandler","value","isValidString","encodeURIComponent","isNumber","windowEventTracker","adCallbacks","AdCallbacks","isLinearAdActive","ads","getContainer","getAdModuleInfo","getModuleInfo","version","currentTime","getCurrentTime","register","Play","issuer","onPlay","Paused","onPause","AdStarted","onAdStarted","AdFinished","onAdFinished","AdBreakStarted","onAdBreakStarted","AdBreakFinished","onAdBreakFinished","AdClicked","onAdClicked","AdQuartile","onAdQuartile","AdSkipped","onAdSkipped","AdError","onAdError","AdManifestLoaded","onAdManifestLoaded","handlePageClose","onBeforeUnload","addEventListener","Bitmovin8AdModule","queue","unloadQueue","syncQueue","adQueue","flushTo","backend","QueueBackend","from","to","eventObject","EventDebugging","s","isEmpty","trim","endsWith","suffix","String","prototype","substring","startsWith","prefix","getInstance","Logger","instance","initialize","analyticsDebugConfig","log","message","enabled","console","optionalParams","table","tabularData","properties","warn","errorMessageToUser","padRight","str","Array","join","BITMOVIN_ANALYTICS_AUGMENTED_MARKER","_sample","NoOpBackend","Event","JSM_INITIAL_EVENT","hasAdModule","backendBaseUrl","licenseKey","analyticsCall","AnalyticsCall","key","noOp","RemoteBackend","trackedObjects","eventName","func","release","obj","pop","removeEventListener","WindowEventTracker","State","stateMachineCallbacks","playingHeartbeatService","opts","debuggingStates","enabledDebugging","getAllStatesBut","states","getAllStates","i","keys","map","createStateMachine","StateMachine","create","initial","state","SETUP","customStateMachineErrorCallback","events","SOURCE_LOADED","ERROR","SOURCE_CHANGING","INITIAL_SOURCE_CHANGE","READY","PLAY","STARTUP","PLAYING","stayIn","VIDEO_CHANGE","AUDIO_CHANGE","AD_STARTUP","VIDEOSTART_FAILED","UNLOAD","VIDEOSTART_TIMEOUT","TIMECHANGED","START_BUFFERING","END_BUFFERING","PAUSE","REBUFFERING","QUALITYCHANGE","QUALITYCHANGE_PAUSE","SEEK","PLAY_SEEKING","END_PLAY_SEEKING","SEEKED","END","CUSTOM_DATA_CHANGE","CUSTOMDATACHANGE","SUBTITLE_CHANGE","SUBTITLE_CHANGING","AUDIOTRACK_CHANGED","AUDIOTRACK_CHANGING","START_AD","END_AD","AD_READY","AD_PAUSE","AD_PLAYING","MUTE","MUTING_READY","UN_MUTE","MUTING_PLAY","MUTING_PAUSE","START_CAST","CASTING","END_CAST","MANUAL_SOURCE_CHANGE","SOURCE_UNLOADED","QUALITYCHANGE_REBUFFERING","onbeforeevent","_event","_eventTimestamp","_eventData","_from","eventTimestamp","eventData","seekDuration","seekStartTimestamp","setVideoTimeEndFromEvent","end_play_seeking","stopHeartbeat","onleavestate","logStateMachineTransition","resetRebufferingHelpers","addStatesToLog","stateDuration","onEnterStateTimestamp","lastTrackedVideoEndObject","clearVideoStartTimeout","setVideoStartTimeout","lowerCaseFrom","toLowerCase","videoStartFailed","createVideoStartFailedReason","unload","setVideoTimeStartFromEvent","ad","defaultStateMachineCallbackFn","logMissingCallbackWarning","videoChange","audioChange","mute","unMute","startHeartbeat","_to","onenterstate","starttime","startCasting","startRebufferingHeartbeatInterval","onafterevent","initialSourceChange","manualSourceChange","stateMachine","FINISH_QUALITYCHANGE_PAUSE","FINISH_QUALITYCHANGE","FINISH_QUALITYCHANGE_REBUFFERING","FINISH_MUTING","onSsaiPlaybackInteraction","currentState","sendPlayingSample","getStates","setEnabledDebugging","AnalyticsStateMachine","Bitmovin8AnalyticsStateMachine","VERSION","Result","SUCCEEDED","NOTRANSITION","CANCELLED","PENDING","Error","INVALID_TRANSITION","PENDING_TRANSITION","INVALID_CALLBACK","WILDCARD","ASYNC","cfg","target","terminal","fsm","transitions","add","isArray","n","hasOwnProperty","buildEvent","current","is","can","transition","cannot","concat","isFinished","msg","sort","defer","doCallback","apply","beforeAnyEvent","afterAnyEvent","leaveAnyState","enterAnyState","changeState","beforeThisEvent","afterThisEvent","leaveThisState","enterThisState","beforeEvent","afterEvent","leaveState","specific","general","enterState","call","arguments","cancel","leave","defaultStateMachineCallbacks","qualityChangeService","ssaiService","SsaiService","_onLicenseKeyReceived","_onLicenseCallFailed","sourceInfoFallbackService","SourceInfoFallbackService","drmPerformanceInfo","_windowEventTracker","eventCallback","callEvent","getCurrentTimestamp","segmentsDownloadCount","segmentsDownloadSize","segmentsDownloadTime","avgDownloadSpeed","minDownloadSpeed","maxDownloadSpeed","avgTimeToFirstByte","resetIntervals","resetSourceRelatedState","getCommonPlaybackInfo","scale","devicePixelRatio","screenHeight","screen","height","screenWidth","width","clearValues","clearSegments","reset","setCustomData","values","previousState","customdatachange","isAudioMuted","playerIsMuted","currentVolume","InternalAdapter","DEFAULT_HEARTBEAT_INTERVAL_MS","getPlayerCurrentTime","setListener","listener","heartbeatInterval","clearHeartbeat","setInterval","onHeartbeat","clearTimeout","HeartbeatService","replace","c","r","Math","random","toString","createBackend","analyticsConfig","licensingRequest","adapter","authenticationCallback","isEnabled","inner","createInnerBackend","decorateWithDebuggingBackend","debug","DebuggingBackend","decorateWithBackendFromConfigIfAvailable","innerBackend","wrapBackend","backendUrl","ANALYTICS_BACKEND_BASE_URL","LicenseCheckingBackend","LicenseCall","sequenceNumberAssigningBackend","SequenceNumberBackend","BackendFactory","_items","offer","item","poll","shift","clear","limit","maxElements","Queue","playerVideoDuration","Number","isNaN","Infinity","code","BITMOVIN_PLAYER_LICENSING_ERROR","ErrorCode","SETUP_MISSING_LICENSE_WHITELIST","QUALITY_CHANGE_THRESHOLD_EXCEEDED","BUFFERING_TIMEOUT_REACHED","VIDEO_STARTUP_TIMEOUT_REACHED","info","licenseCall","licenseKeyReceived","eventArgs","licenseLazyLoadingTimeoutHandle","unsubscribeFromAdapter","promise","wrapLicenseCheckPromiseWithCallback","performLicenseCheck","licenseCallFailed","authenticationCompleted","licenseLazyLoadingTimeout","supportsDeferredLicenseLoading","onLicenseKeyReceived","onLicenseCallFailed","setTimeout","ANALYTICS_LICENSECALL_TIMEOUT","status","LicensingResult","Denied","then","result","Granted","remoteBackend","catch","err","response","features","stateMachineEvent","VideoStartFailedReason","PLAYER_ERROR","PAGE_CLOSED","TIMEOUT","UNKNOWN","AD_TYPE","element","onIntersectionChanged","threshold","inViewport","options","rootMargin","observer","IntersectionObserver","entries","handleIntersect","observe","_error","hidden","Utils","getHiddenProp","visibilityChange","document","handleVisibilityChange","bind","isHidden","isInViewport","dispose","unobserve","disconnect","_observer","intersectionRatio","ViewportTracker","download","Measure","sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition","anything","maybeSsaiAdBreakMetadata","adPosition","SsaiState","eventHandler","adIndex","IDLE","isFirstSampleOfAd","sentAdQuartiles","errorSent","activate","adBreakStart","adBreakMetadata","isActivated","AD_BREAK_STARTED","currentAdMetadata","adStart","adMetadata","getTime","playerCurrentTime","reportPlaybackInteraction","ACTIVE","resetAdData","adId","adSystem","customData","currentAdImpressionId","timestampOfAdStart","getCurrentMonotonicTimestampInMs","reportEngagementInteraction","type","adQuartileFinished","adQuartile","adQuartileMetadata","includes","quartile","quartileMetadata","timeSinceAdStartedInMs","getMonotonicTimestampInMsSince","adBreakEnd","resetAdBreakData","manipulate","SSAI","customDataValuesKeys","SSAI_RELATED_SAMPLE_MARKER","sendAdEngagementErrorSample","errorCode","errorMessage","initialAnalyticsConfig","backendFactory","sessionHandler","featureManager","onErrorDetailEventDispatcher","pageLoadTime","playerStartupTime","videoStartupTime","autoplay","droppedSampleFrames","startupTime","featureConfigs","configureFeatures","sourceChange","guardConfigChangeAgainstMissingTitle","guardConfigChangeAgainstMissingIsLive","guardAgainstDuplicatedUserId","newConfig","mergeAnalyticsConfig","setCustomDataOnce","oldConfig","setState","sendAnalyticsRequestAndClearValues","setConfigParameters","setAutoDetectedDeviceInformation","getCurrentImpressionId","impressionId","getUserId","changeCustomData","extractCustomDataFieldsOnly","that","errorDetailTrackingSettingsProvider","getDomainFromAnalyticsConfig","licenseKeyReceivedUnsubscriber","setupSample","init","setupStateMachineCallbacks","registerFeatures","adModule","adAnalytics","AdAnalytics","getPlayerInformationFromAdapter","getPlayerName","getPlayerVersion","playerTech","getPlayerTech","resetFeatures","generateNewImpressionId","setUserId","videoCompletionTracker","resetValues","stopResetInterval","playerKey","deviceInformation","getDeviceInformationFromAnalyticsConfig","cdnProvider","videoId","videoTitle","title","customUserId","transferCustomDataFields","experimentName","model","hasWindowWebOSApi","modelName","getWebOSTVModelName","analyticsVersion","setDuration","performance","timing","loadTime","navigationStart","startup","supportedVideoCodecs","supportedVideoFormats","sanitizedStartupDuration","max","startupTimeSum","getAutoPlay","setStartupHasFinished","drmPerformance","getDrmPerformanceInfo","drmType","drmLoadTime","playing","setCompletionValues","videoStartForClosedState","videoTimeStart","videoTimeEnd","setVideoTimeStart","setVideoTimeEnd","heartbeat","heartbeatPayload","qualitychange","sendQualityChange","qualitychange_pause","qualitychange_rebuffering","setPlaybackVideoPropertiesFromEvent","setPlaybackAudioPropertiesFromEvent","audiotrack_changing","pause","paused","sendSeekingSample","seeked","seeking","paused_seeking","rebuffering","buffered","reason","videoStartFailedReason","errorData","legacyData","errorSegments","segments","onError","data","CSAI","isMuted","subtitle_changing","calculateTime","playlistTransition","end","_duration","_state","videoPlaybackWidth","videoPlaybackHeight","bitrate","videoBitrate","videoCodec","audioBitrate","audioCodec","setPlaybackInfoFromAdapter","getCurrentPlaybackInfo","isLive","videoDuration","streamFormat","mpdUrl","m3u8Url","progUrl","videoWindowWidth","videoWindowHeight","isBoolean","isCasting","castTech","audioLanguage","subtitleEnabled","subtitleLanguage","droppedFrames","platform","pageLoadType","getPageLoadType","path","sanitizePath","location","pathname","language","navigator","userLanguage","userAgent","PlayerSize","Window","time","completedTotal","sendAnalyticsRequest","customDataOnceValues","downloadSpeedInfo","setQualityInfoOnSample","copySample","sendSsaiEngagementAdSample","ssaiEngagementTrackingEnabled","isSsaiEngagementStartedData","ssaiAdSample","createStartedAdSample","isSsaiEngagementQuartileData","createQuartileAdSample","isSsaiEngagementErrorData","ssaiErrorAdSample","createErrorAdSample","completed","addWatched","start","getCompletionPercentage","startResetInterval","increaseCounter","isQualityChangeEventEnabled","FeatureManager","playbackInfo","CdnProvider","HttpRequestType","clicked","closed","midpoint","quartile1","quartile3","skipped","started","adClickthroughUrl","clickThroughUrl","id","mediaUrl","mediaFileUrl","mediaUrlDetails","getHostnameAndPathFromUrl","mediaPath","mediaServer","hostname","isLinear","adPlaybackHeight","adPlaybackWidth","mimeType","advertiser","advertiserName","apiFramework","creative","creativeAdId","creativeId","universalAdId","universalAdIdRegistry","idRegistry","universalAdIdValue","adDescription","minSuggestedDuration","calculateTimeWithUndefined","survey","surveyUrl","uri","adTitle","wrapperAdsCount","wrapperAdIds","linearAd","adSkipAfter","AdSample","parseSkipAfter","skippableAfter","adSkippable","skippable","adDuration","skipAfter","MESSAGE_NAMESPACE","ANALYTICS_VIDEOSTART_TIMEOUT","ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD","ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL","ANALYTICS_REBUFFER_TIMEOUT","ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD","SEQUENCE_NUMBER_LIMIT","ssai","isDefined","internalAdapter","adBreakMetadataWithValidAdPosition","hasValidSsaiAdBreakMetadataStructure","sanitizedAdBreakMetadata","simplySanitizeSsaiAdBreakMetadata","hasValidSsaiAdMetadataStructure","sanitizedAdMetadata","simplySanitizeSsaiAdMetadata","hasValidSsaiAdQuartileStructure","sanitizedSsaiAdQuartileMetadata","sanitizeSsaiAdQuartileMetadata","hasPlayerAlreadyBeenAugmented","markPlayerInstanceAsAugmented","playerConfig","sanitizedConfig","sanitizeAnalyticsConfig","Bitmovin8InternalAdapter","wrapPlayerLoad","originalLoad","load","casting","muting_ready","setStreamFormat","applyStreamFormat","applyAndStoreCodecInfo","codecInfo","attributes","newCookie","cookie","cname","split","charAt","hiddenProp","PAGE_LOAD_TYPE","BACKGROUND","FOREGROUND","toBoolean","Boolean","valueOf","isObject","isPlainObject","round","getCustomDataString","fromConfig","toConfig","CustomDataUtils","customDataFieldCount","customDataField","getDocumentPropWithPrefix","prop","pascalCase","toUpperCase","isVideoInFullscreen","fullscreenProp","nodeName","domElement","createElement","href","calculatePercentage","numerator","denominator","getURLResourceName","joinUrls","reduce","prev","substr","getSourceInfoFromBitmovinSourceConfig","progressive","progBitrate","playbackVideoData","getPlaybackVideoData","progressiveArrayIndex","baseUrl","licenseServerUrl","post","analyticsServerUrl","adAnalyticsServerUrl","analyticsUrl","isSsaiRelatedSample","appendSsaiRoutingParam","trySendBeacon","fallbackFunction","requestHeaders","sendBeacon","blob","Blob","adSample","adAnalyticsUrl","_issuer","match","input","retVal","bytesToBits","bytes","bitsToBytes","bits","kiloBitsToBits","kiloBits","Converter","videoImpressionId","AdAnalyticsSample","CastTech","addSegment","segment","removeSegment","getSegments","SegmentTracker","isAdPosition","maybeSsaiAdMetadata","ssaiAdMetadata","sanitizedCustomDataValues","extracted","isSsaiAdQuartile","ssaiAdQuartileMetadata","failedBeaconUrl","ViewMode","speedMeter","segmentTracker","httpRequestTrackingAdapter","onBeforeUnLoadEvent","BITMOVIN","getPlayerType","getInfo","_adModule","isAdPlaying","lastTrackedCurrentTime","currentAd","getActiveAd","registerPlayerEventListeners","registerUnloadEventListeners","ssaiEngagementInteractionData","requestTracking","HttpRequestTracking","ErrorDetailTracking","ErrorDetailBackend","errorDetailSubscribable","playback","getViewMode","Fullscreen","normalizeVideoDuration","getStreamType","offsetWidth","offsetHeight","getAudio","lang","getSource","getDroppedVideoFrames","applySubtitleProperties","applyPlaybackQualityProperties","applyCastingProperties","applySourceProperties","callManualSourceChangeEvent","SourceUnloaded","SourceLoaded","getDuration","setVideoDuration","CastStarted","CastStopped","Playing","TimeChanged","Seek","allowSeeking","Seeked","StallStarted","StallEnded","AudioPlaybackQualityChanged","audioQualityChangedData","sourceQuality","targetQuality","shouldAllowAudioQualityChange","setAudioBitrate","VideoPlaybackQualityChanged","videoQualityChangedData","shouldAllowVideoQualityChange","setVideoBitrate","ViewModeChanged","START_FULLSCREEN","END_FULLSCREEN","Muted","Unmuted","additionalData","PlaybackFinished","AudioChanged","SubtitleEnabled","SubtitleDisabled","LicenseValidated","handleCollectorUnload","Destroy","source","dash","hls","progSourceInfo","enabledSubtitle","subtitles","list","find","videoQuality","audioQuality","getPlaybackAudioData","isAirplayActive","AirPlay","remoteControlConfig","remotecontrol","GoogleCast","WebSocket","seekEvent","abs","position","seekTarget","AnalyticsSettings","DownloadSpeedMeter","SegmentTrackerAdapter","getSegmentTracker","HttpRequestTrackingAdapter","TimespanOverlappingType","watched","overlappingTimespan","mergeWatched","w","time1","k","time2","overlapType","getOverlappingType","Overlapping","mergeAndReplace","getOverlappingTimespan","FirstContainedInSecond","SecondContainedInFirst","None","first","second","isMomentInTimespan","moment","timespan","firstIndex","secondIndex","newWatchedTimespan","unregisterFeatures","feature","constructor","adConfig","adManifestLoadedEvent","adFallbackIndex","manifestDownloadTime","downloadTiming","adReplaceContentDuration","replaceContentDuration","currentFallbackIndex","adBreakConfig","adOffset","adPreloadOffset","preloadOffset","adTagConfig","adIsPersistent","persistent","tag","fallbackTags","adTagType","adTagUrl","adTagDetails","adTagServer","adTagPath","adBreak","adScheduleTime","scheduleTime","adIdPlayer","AdBreakSample","underlying","sequenceNumber","updateSampleBeforeSending","isSequenceNumberAboveThreshold","fields","debugFields","printFields","f","eventDispatcher","playerExports","onDownloadFinished","httpRequest","mapHttpRequestType","REBUFFERING_HEARTBEAT_INTERVALS","videoStartupTimeoutMs","Settings","rebufferTimeoutMs","currentRebufferingIntervalIndex","stateMachineEventMethod","playbackCurrentTimeInSeconds","clearRebufferingTimeoutHandle","clearRebufferingHeartbeatHandle","startRebufferingTimeoutHandle","rebufferingHeartbeatIntervalHandle","min","clearInterval","rebufferingTimeoutHandle","videoStartTimeout","triggeredBySsai","payload","_queue","_enabled","copyErrorDetailTruncateStringsAndUrls","errorDetail","maxStringLength","maxUrlLength","copyErrorDataTruncateStrings","httpRequests","request","copyHttpRequestTruncateUrls","maxLength","lastRedirectLocation","exceptionMessage","copyErrorDetailTruncateHttpRequests","maxRequests","limitHttpRequestsOfQueuedErrorDetails","errorDetailCopy","MAX_STRING_LENGTH","MAX_URL_LENGTH","flush","copy","removeFromQueue","findIndex","subscribables","_maxRequests","DEFAULT_MAX_REQUESTS","_httpRequestQueue","onDownloadFinishedHandler","addRequest","subscribable","items","adType","ROUTING_URL_PARAM","ROUTING_URL_PARAM_VALUE_SSAI","playbackSample","ssaiEngagementErrorData","buildAdSample","ssaiEngagementStartedData","ssaiEngagementQuartileData","timestampInMs","adEngagementSample","customData1","customData2","customData3","customData4","customData5","customData6","customData7","customData8","customData9","customData10","customData11","customData12","customData13","customData14","customData15","customData16","customData17","customData18","customData19","customData20","customData21","customData22","customData23","customData24","customData25","customData26","customData27","customData28","customData29","customData30","customData31","customData32","customData33","customData34","customData35","customData36","customData37","customData38","customData39","customData40","customData41","customData42","customData43","customData44","customData45","customData46","customData47","customData48","customData49","customData50","adImpressionId","quartile1FailedBeaconUrl","midpointFailedBeaconUrl","quartile3FailedBeaconUrl","completedFailedBeaconUrl","floor","whileIn","stateMachineEventDefBuilderFn","runEventCallbacksFor","passOver","_ex","loggerMessage","loggerMessageData","ignoreStates","ignoredState","deviceType","deviceClass","origin","oldConfigWithoutSourceRelatedFields","sourceSpecificProperties","customDataFieldsRegex","removeSourceRelatedFields","mergedCollectorConfig","oldCollectorConfig","newCollectorConfig","mergeCollectorConfig","webOSSystem","deviceInfo","PalmSystem","handleSegmentPlaybackEvent","SegmentPlayback","adManifestLoadedEvents","isPlaying","adPodPosition","viewportTracker","clearCurrentTimeInterval","activeAdSample","isContainerInViewport","enterViewportTimestamp","timeInViewport","beginPlayingTimestamp","updatePlayingTime","activeAdBreakSample","getAdManifestLoadedEvent","adStartupTimestamp","resetActiveAd","adStartupTime","startAd","completeAd","skipPosition","skipPercentage","errorPosition","adBreakSample","errorPercentage","clickPosition","clickPercentage","FIRST_QUARTILE","MIDPOINT","THIRD_QUARTILE","closePosition","closePercentage","createNewAdAnalyticsSample","analyticsSample","moduleInfo","adModuleVersion","percentageInViewport","timePlayed","currentTimeInterval","TIMEOUT_CURRENT_TIME_INTERVAL","exitPosition","playPercentage","MODULE_NAME","settingsProvider","httpRequestTracking","errorIndex","onErrorHandler","httpRequestsCopy","errorId","exceptionStacktrace","_authenticated","numberOfHttpRequests","errorDetails","measures","measurement","measure","speed","m","ceil","totalTime","avgSpeed","minSpeed","maxSpeed","a","b","totalSpeed","speeds","numMeasurements","bytePerSecondToBitPerSecond","bps","avg","qualityChangeThreshold","qualityChangeCount","previousVideoBitrate","previousAudioBitrate","startupHasFinished","newBitrate","resetIntervalId","resetCounter","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__","adapters"],"sourceRoot":""}
1
+ {"version":3,"file":"bitmovin-analytics-bitmovin-player.js","mappings":"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","sources":["webpack://bitmovin.analytics/webpack/universalModuleDefinition","webpack://bitmovin.analytics/./src/utils/Http.ts","webpack://bitmovin.analytics/./src/features/Feature.ts","webpack://bitmovin.analytics/./src/core/LongPlaytimeFilteringBackend.ts","webpack://bitmovin.analytics/./src/utils/CodecHelper.ts","webpack://bitmovin.analytics/./src/enums/Player.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/SpeedMeterAdapter.ts","webpack://bitmovin.analytics/./src/core/EventDispatcher.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/playerModule.ts","webpack://bitmovin.analytics/./src/core/SessionPersistenceHandler.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8AdModule.ts","webpack://bitmovin.analytics/./src/core/QueueBackend.ts","webpack://bitmovin.analytics/./src/utils/EventDebugging.ts","webpack://bitmovin.analytics/./src/utils/stringUtils.ts","webpack://bitmovin.analytics/./src/utils/Logger.ts","webpack://bitmovin.analytics/./src/utils/playerAugmentationUtils.ts","webpack://bitmovin.analytics/./src/enums/MIMETypes.ts","webpack://bitmovin.analytics/./src/core/NoOpBackend.ts","webpack://bitmovin.analytics/./src/enums/Event.ts","webpack://bitmovin.analytics/./src/core/RemoteBackend.ts","webpack://bitmovin.analytics/./src/utils/WindowEventTracker.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/bitmovin8/Bitmovin8AnalyticsStateMachine.ts","webpack://bitmovin.analytics/./node_modules/javascript-state-machine/state-machine.js","webpack://bitmovin.analytics/./src/adapters/internal/InternalAdapter.ts","webpack://bitmovin.analytics/./src/core/HeartbeatService.ts","webpack://bitmovin.analytics/./src/utils/uuidUtils.ts","webpack://bitmovin.analytics/./src/core/BackendFactory.ts","webpack://bitmovin.analytics/./src/utils/Queue.ts","webpack://bitmovin.analytics/./src/types/PlaybackInfo.ts","webpack://bitmovin.analytics/./src/enums/ErrorCode.ts","webpack://bitmovin.analytics/./src/core/LicenseCheckingBackend.ts","webpack://bitmovin.analytics/./src/enums/VideoStartFailedReason.ts","webpack://bitmovin.analytics/./src/enums/AdType.ts","webpack://bitmovin.analytics/./src/utils/ViewportTracker.ts","webpack://bitmovin.analytics/./src/core/Measure.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/bitmovin8AdapterSsaiApiSanitizeUtils.ts","webpack://bitmovin.analytics/./src/core/ssai/SsaiService.ts","webpack://bitmovin.analytics/./src/core/Analytics.ts","webpack://bitmovin.analytics/./src/enums/CDNProvider.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/bitmovin8PlayerTypes.ts","webpack://bitmovin.analytics/./src/types/AdSample.ts","webpack://bitmovin.analytics/./src/types/LicensingRequest.ts","webpack://bitmovin.analytics/./src/utils/Settings.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8Adapter.ts","webpack://bitmovin.analytics/./src/types/StateMachineCallbacks.ts","webpack://bitmovin.analytics/./src/core/SourceInfoFallbackService.ts","webpack://bitmovin.analytics/./src/utils/Version.ts","webpack://bitmovin.analytics/./src/utils/documentCookieUtils.ts","webpack://bitmovin.analytics/./src/utils/Utils.ts","webpack://bitmovin.analytics/./src/utils/BitmovinProgressiveSourceHelper.ts","webpack://bitmovin.analytics/./src/utils/LicenseCall.ts","webpack://bitmovin.analytics/./src/utils/AnalyticsCall.ts","webpack://bitmovin.analytics/./src/adapters/internal/ads/AdModuleAPI.ts","webpack://bitmovin.analytics/./src/types/CustomDataValues.ts","webpack://bitmovin.analytics/./src/utils/Converter.ts","webpack://bitmovin.analytics/./src/types/AdAnalyticsSample.ts","webpack://bitmovin.analytics/./src/enums/CastTech.ts","webpack://bitmovin.analytics/./src/core/SegmentTracker.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiApiUtils.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/Bitmovin8InternalAdapter.ts","webpack://bitmovin.analytics/./src/core/VideoCompletionTracker.ts","webpack://bitmovin.analytics/./src/features/FeatureManager.ts","webpack://bitmovin.analytics/./src/enums/StreamTypes.ts","webpack://bitmovin.analytics/./src/types/AdBreakSample.ts","webpack://bitmovin.analytics/./src/core/SequenceNumberBackend.ts","webpack://bitmovin.analytics/./src/core/DebuggingBackend.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/HttpRequestTrackingAdapter.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/AnalyticsStateMachine.ts","webpack://bitmovin.analytics/./src/features/errordetails/ErrorDetailBackend.ts","webpack://bitmovin.analytics/./src/core/IdenticalErrorReportingLimiter.ts","webpack://bitmovin.analytics/./src/features/httprequesttracking/HttpRequestTracking.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiUtils.ts","webpack://bitmovin.analytics/./src/analyticsStateMachines/stateMachineUtils.ts","webpack://bitmovin.analytics/./src/utils/analyticsConfigUtils.ts","webpack://bitmovin.analytics/./src/utils/WebOSUtils.ts","webpack://bitmovin.analytics/./src/enums/PlayerSize.ts","webpack://bitmovin.analytics/./src/adapters/bitmovin8/player/SegmentTrackerAdapter.ts","webpack://bitmovin.analytics/./src/core/AdAnalytics.ts","webpack://bitmovin.analytics/./src/core/ssai/ssaiEngagementInteractionData.ts","webpack://bitmovin.analytics/./src/features/errordetails/ErrorDetailTracking.ts","webpack://bitmovin.analytics/./src/core/DownloadSpeedMeter.ts","webpack://bitmovin.analytics/./src/core/QualityChangeService.ts","webpack://bitmovin.analytics/./src/enums/PageLoadType.ts","webpack://bitmovin.analytics/webpack/bootstrap","webpack://bitmovin.analytics/./src/bitmovin-analytics-bitmovin-player.ts"],"sourcesContent":["(function webpackUniversalModuleDefinition(root, factory) {\n\tif(typeof exports === 'object' && typeof module === 'object')\n\t\tmodule.exports = factory();\n\telse if(typeof define === 'function' && define.amd)\n\t\tdefine([], factory);\n\telse if(typeof exports === 'object')\n\t\texports[\"bitmovin\"] = factory();\n\telse\n\t\troot[\"bitmovin\"] = root[\"bitmovin\"] || {}, root[\"bitmovin\"][\"analytics\"] = factory();\n})(self, function() {\nreturn ","import {logger} from './Logger';\n\nexport function post(url: string, body: any, callback: any, async = true): void {\n let xhttp: any;\n let isLegacyXDomainRequestUsed = false;\n\n if ((window as any).XDomainRequest) {\n // XDomainRequest is the only way of having an XHR that supports CORS in IE8 and 9. At the time of IE8,\n // Microsoft decided to come up with their own CORS XHR instead of the standard CORS XMLHttpRequest\n // which is now used in IE10.\n // Since IE10, XDomainRequest has been deprecated and since IE11 removed.\n xhttp = new (window as any).XDomainRequest();\n isLegacyXDomainRequestUsed = true;\n } else {\n xhttp = new XMLHttpRequest();\n }\n\n const responseCallback = () => {\n if (xhttp.readyState == XMLHttpRequest.DONE) {\n if (xhttp.responseText <= 0) {\n return;\n }\n\n const sampleResponse = JSON.parse(xhttp.responseText);\n\n callback(sampleResponse);\n }\n };\n\n if (isLegacyXDomainRequestUsed) {\n xhttp.onload = responseCallback;\n } else {\n xhttp.onreadystatechange = responseCallback;\n }\n\n try {\n xhttp.open('POST', url, async);\n\n // XDomainRequest restriction: No custom headers may be added to the request\n // https://learn.microsoft.com/en-us/archive/blogs/ieinternals/xdomainrequest-restrictions-limitations-and-workarounds\n if (!isLegacyXDomainRequestUsed) {\n xhttp.setRequestHeader('Content-Type', 'text/plain');\n }\n\n xhttp.send(JSON.stringify(body));\n } catch (e) {\n logger.error('Failed to send POST request.', e);\n }\n}\n","import {isNotNullish} from '../utils/Utils';\n\nimport {FeatureConfig} from './FeatureConfig';\n\nexport abstract class Feature<TConfigContainer, TConfig extends FeatureConfig> {\n private _config?: TConfig = undefined;\n private _isEnabled = true;\n\n get config(): TConfig | undefined {\n return this._config;\n }\n\n get isEnabled(): boolean {\n return this._isEnabled;\n }\n\n abstract reset(): void;\n abstract enabled(): void;\n abstract disabled(): void;\n abstract configured(authenticated: boolean, config?: TConfig): void;\n\n disable() {\n this._isEnabled = false;\n this.disabled();\n }\n\n configure(authenticated: boolean, configContainer?: TConfigContainer): TConfig | undefined {\n if (isNotNullish(configContainer)) {\n this._config = this.extractConfig(configContainer);\n }\n this.configured(authenticated, this._config);\n return this._config;\n }\n\n abstract extractConfig(configContainer: TConfigContainer): TConfig | undefined;\n}\n","import {Sample} from '../types/Sample';\nimport {isNullish} from '../utils/Utils';\n\nimport {Backend} from './Backend';\n\n/**\n * The `LongPlaytimeFilteringBackend` is a decorator class that filters out samples\n * where the `played` time exceeds a specified threshold.\n *\n * If a sample's `played` time surpasses the threshold, it is not forwarded to the next backend.\n * Otherwise, the sample is passed along to the next backend for further processing.\n *\n * @implements {Backend}\n */\nexport class LongPlaytimeFilteringBackend implements Backend {\n nextBackend: Backend;\n\n constructor(next: Backend) {\n this.nextBackend = next;\n }\n\n sendRequest(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n if (this.isPlayedAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: any) {\n this.nextBackend.sendAdRequest(sample);\n }\n\n private isPlayedAboveThreshold(sample: Sample): boolean {\n return (isNullish(sample.played) ? 0 : sample.played) >= 90000;\n }\n}\n","const videoFormatCodecMap: {[format: string]: string[]} = {\n avc: ['video/mp4; codecs=\"avc1.42000a\"'],\n vp9: ['video/mp4; codecs=\"vp09.00.50.08\"'],\n av1: ['video/mp4; codecs=\"av01.0.08M.08\"'],\n hevc: ['video/mp4; codecs=\"hev1.1.6.L93.B0\"'],\n};\n\nexport class CodecHelper {\n static get supportedVideoFormats(): string[] | undefined {\n if (!('MediaSource' in window)) {\n return undefined;\n }\n const codecs = Object.getOwnPropertyNames(videoFormatCodecMap).filter((format) =>\n videoFormatCodecMap[format].some((codec) => this.isCodecSupported(codec)),\n );\n return codecs;\n }\n\n static isCodecSupported(codec: string): boolean {\n if (!('MediaSource' in window)) {\n return false;\n }\n\n return MediaSource.isTypeSupported(codec);\n }\n}\n","export enum Player {\n AMAZON_IVS = 'amazonivs',\n BITMOVIN = 'bitmovin',\n BITMOVIN_PWX = 'bitmovin-pwx',\n CHROMECAST_SHAKA = 'chromecast-shaka',\n DASHJS = 'dashjs',\n HLSJS = 'hlsjs',\n HTML5 = 'html5',\n JW = 'jw',\n RADIANT = 'radiant',\n SHAKA = 'shaka',\n VIDEOJS = 'videojs',\n}\n","import type {PlayerAPI} from 'bitmovin-player';\n\nimport {DownloadSpeedMeter} from '../../../core/DownloadSpeedMeter';\n\nexport class SpeedMeterAdapter {\n private meter: DownloadSpeedMeter;\n\n constructor(player: PlayerAPI, meter: DownloadSpeedMeter) {\n this.meter = meter;\n player.on(player.exports.PlayerEvent.DownloadFinished, (event) => this.handleOnDownloadFinishEvent(event));\n }\n\n getDownloadSpeedMeter(): DownloadSpeedMeter {\n return this.meter;\n }\n\n handleOnDownloadFinishEvent(event: any) {\n if (!event.success) {\n return;\n }\n if (event.downloadType.indexOf('media/video') === 0) {\n this.meter.addMeasurement({\n duration: event.downloadTime,\n size: event.size,\n timeToFirstByte: event.timeToFirstByte,\n timestamp: new Date(),\n httpStatus: event.httpStatus,\n });\n }\n }\n}\n","export interface Subscribable<TArgs> {\n subscribe(callback: EventHandler<TArgs>): () => void;\n unsubscribe(callback: EventHandler<TArgs>);\n}\n\ntype EventHandler<TArgs> = (args: TArgs) => void;\n\nexport class EventDispatcher<TArgs> implements Subscribable<TArgs> {\n private callbacks: Array<EventHandler<TArgs>> = [];\n\n subscribe(callback: EventHandler<TArgs>): () => void {\n this.callbacks.push(callback);\n\n return () => this.unsubscribe(callback);\n }\n\n dispatch(args: TArgs) {\n const callbacks = this.callbacks.slice(0);\n callbacks.forEach((callback) => {\n callback(args);\n });\n }\n\n unsubscribe(callback: EventHandler<TArgs>) {\n const index = this.callbacks.indexOf(callback);\n if (index > -1) {\n this.callbacks.splice(index, 1);\n }\n }\n\n get subscriberCount() {\n return this.callbacks.length;\n }\n}\n","import {Bitmovin8Adapter} from './Bitmovin8Adapter';\n\n/*\n * @see https://github.com/bitmovin-engineering/bitdash/blob/ccd3227dac82d1416a471711b40ee0f65d7f9ddb/src/ModuleDefinition.ts#L17\n */\nexport const PlayerModule = {\n name: 'analytics',\n module: {\n Analytics: Bitmovin8Adapter,\n },\n hooks: {\n setup: (module: any, player: any) => {\n const config = player.getConfig();\n const isConfigMissing = !config;\n const isAnalyticsDisabled = config?.analytics === false;\n\n if (isConfigMissing || isAnalyticsDisabled) {\n return Promise.resolve();\n }\n\n const analyticsBitmovin8Adapter = module.Analytics;\n const analyticsModuleInstance = new analyticsBitmovin8Adapter(player);\n return Promise.resolve(analyticsModuleInstance);\n },\n },\n} as const;\n","import type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport {deleteCookie, getCookie, setCookie} from '../utils/documentCookieUtils';\nimport {isBlank, isValidString} from '../utils/stringUtils';\nimport {isNullish, isNumber} from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\n\nexport const COOKIE_NAME_BITMOVIN_ANALYTICS_UUID = 'bitmovin_analytics_uuid';\n/** One year in seconds */\nexport const COOKIE_DEFAULT_MAX_AGE = 365 * 24 * 60 * 60;\n\nexport class SessionPersistenceHandler {\n readonly userId: string;\n\n constructor(config: AnalyticsConfig) {\n const collectorConfig = config.config;\n\n const shouldNotUseCookies = collectorConfig?.cookiesEnabled === false;\n\n if (shouldNotUseCookies) {\n deleteCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID);\n this.userId = generateUUID();\n return;\n }\n\n const existingUserId = getCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID);\n this.userId = !isBlank(existingUserId) ? existingUserId : generateUUID();\n\n const cookieDomain = validateCookieDomainValue(collectorConfig?.cookiesDomain);\n const cookieMaxAge = validateCookieMaxAgeValue(collectorConfig?.cookiesMaxAge);\n\n // we set also expires, because max-age is not supported on old browsers like IE8\n const nowMillis = Date.now();\n const expirationDate = new Date(nowMillis + cookieMaxAge * 1000);\n const cookieExpires = expirationDate.toUTCString();\n\n setCookie(COOKIE_NAME_BITMOVIN_ANALYTICS_UUID, this.userId, {\n domain: cookieDomain,\n expires: cookieExpires,\n maxAge: cookieMaxAge,\n });\n }\n}\n\nexport const validateCookieDomainValue = (value: unknown): string | undefined => {\n if (isNullish(value)) {\n return undefined;\n }\n\n if (!isValidString(value)) {\n return undefined;\n }\n\n if (isBlank(value)) {\n return undefined;\n }\n\n return encodeURIComponent(value);\n};\n\nexport const validateCookieMaxAgeValue = (value: unknown): number => {\n if (isNullish(value)) {\n return COOKIE_DEFAULT_MAX_AGE;\n }\n\n if (!isNumber(value)) {\n return COOKIE_DEFAULT_MAX_AGE;\n }\n\n return value;\n};\n","import type {PlayerAPI, UserInteractionEvent} from 'bitmovin-player';\n\nimport {WindowEventTracker} from '../../utils/WindowEventTracker';\nimport {AdCallbacks, AdModuleAPI} from '../internal/ads/AdModuleAPI';\n\nexport class Bitmovin8AdModule implements AdModuleAPI {\n adCallbacks = new AdCallbacks();\n\n constructor(\n private player: PlayerAPI,\n private windowEventTracker: WindowEventTracker,\n ) {\n this.register();\n }\n\n isLinearAdActive = () => {\n if (this.player.ads) {\n return (this.player.ads as any).isLinearAdActive() || false;\n }\n return false;\n };\n getContainer = () => this.player.getContainer();\n getAdModuleInfo = () => {\n if (this.player.ads) {\n return (this.player.ads as any).getModuleInfo();\n }\n return {name: undefined, version: undefined};\n };\n currentTime = () => this.player.getCurrentTime();\n\n private register() {\n this.player.on(this.player.exports.PlayerEvent.Play, (e: UserInteractionEvent) => {\n if (e.issuer === 'advertising-api') {\n this.adCallbacks.onPlay(e.issuer);\n }\n });\n this.player.on(this.player.exports.PlayerEvent.Paused, (e: UserInteractionEvent) => {\n if (e.issuer === 'advertising-api') {\n this.adCallbacks.onPause(e.issuer);\n }\n });\n this.player.on(this.player.exports.PlayerEvent.AdStarted, (event: any) => {\n this.adCallbacks.onAdStarted(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdFinished, (event: any) => {\n this.adCallbacks.onAdFinished(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdBreakStarted, (event: any) => {\n this.adCallbacks.onAdBreakStarted(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdBreakFinished, (event: any) => {\n this.adCallbacks.onAdBreakFinished(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdClicked, (event: any) => {\n this.adCallbacks.onAdClicked(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdQuartile, (event: any) => {\n this.adCallbacks.onAdQuartile(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdSkipped, (event: any) => {\n this.adCallbacks.onAdSkipped(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdError, (event: any) => {\n this.adCallbacks.onAdError(event);\n });\n this.player.on(this.player.exports.PlayerEvent.AdManifestLoaded, (event: any) => {\n this.adCallbacks.onAdManifestLoaded(event);\n });\n const handlePageClose = () => {\n this.adCallbacks.onBeforeUnload();\n };\n this.windowEventTracker.addEventListener('beforeunload', handlePageClose);\n this.windowEventTracker.addEventListener('unload', handlePageClose);\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\n\nimport {Backend} from './Backend';\n\n/**\n * The `QueueBackend` class is responsible for queuing samples for deferred processing.\n * Samples are stored in different queues depending on the sample type and can be flushed\n * to another backend for further processing.\n *\n * This is useful e.g. to still collect sample data while waiting for a license call to succeed.\n *\n * @implements {Backend}\n */\nexport class QueueBackend implements Backend {\n queue: Sample[] = [];\n unloadQueue: Sample[] = [];\n syncQueue: Sample[] = [];\n adQueue: Array<AdAnalyticsSample & AdBreakSample & AdSample> = [];\n\n sendRequest(sample: Sample) {\n this.queue.push(sample);\n }\n sendUnloadRequest(sample: Sample) {\n this.unloadQueue.push(sample);\n }\n sendRequestSynchronous(sample: Sample) {\n this.syncQueue.push(sample);\n }\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.adQueue.push(sample);\n }\n\n flushTo(backend: Backend) {\n this.queue.forEach((e) => {\n backend.sendRequest(e);\n });\n this.unloadQueue.forEach((e) => {\n backend.sendUnloadRequest(e);\n });\n this.syncQueue.forEach((e) => {\n backend.sendRequestSynchronous(e);\n });\n this.adQueue.forEach((e) => {\n backend.sendAdRequest(e);\n });\n }\n}\n","export class EventDebugging {\n event: string | undefined;\n from: string | undefined;\n to: string | undefined;\n timestamp: number;\n eventObject: any;\n\n constructor(\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n timestamp: number,\n eventObject: any,\n ) {\n this.event = event;\n this.from = from;\n this.to = to;\n this.timestamp = timestamp;\n this.eventObject = eventObject;\n }\n}\n","import {isNotNullish, isNullish} from './Utils';\n\nexport const isValidString = (s: unknown): s is string => isNotNullish(s) && typeof s === 'string';\n\nexport const isEmpty = (s: string | null | undefined): boolean => isNullish(s) || s.length === 0;\n\nexport const isBlank = (s: string | null | undefined): boolean => isEmpty(s) || isEmpty(s?.trim());\n\nexport const endsWith = (s: string, suffix: string): boolean => {\n if (!isValidString(s) || !isValidString(suffix)) {\n return false;\n }\n\n // our target is ES5, so we can't use String.prototype.endsWith without checking for it\n if (isNotNullish(String.prototype.endsWith)) {\n return s.endsWith(suffix);\n }\n\n return s.substring(s.length - suffix.length) === suffix;\n};\n\nexport const startsWith = (s: string, prefix: string): boolean => {\n if (!isValidString(s) || !isValidString(prefix)) {\n return false;\n }\n\n // our target is ES5, so we can't use String.prototype.startsWith without checking for it\n if (isNotNullish(String.prototype.startsWith)) {\n return s.startsWith(prefix);\n }\n return s.substring(0, prefix.length) === prefix;\n};\n","import {AnalyticsConfig} from '../types/AnalyticsConfig';\n\n/**\n * Uses a Singleton design pattern.\n *\n * We want to ensure that only one object of its kind exists and provides a single point of access to it,\n * to be able to control enabled/disabled `console` logs for customer in whole code base.\n */\nclass Logger {\n private static instance: Logger;\n\n static getInstance(): Logger {\n if (!Logger.instance) {\n Logger.instance = new Logger();\n }\n\n return Logger.instance;\n }\n\n private analyticsDebugConfig: Readonly<AnalyticsConfig['debug']>;\n\n private constructor() {}\n\n initialize(analyticsDebugConfig: AnalyticsConfig['debug']) {\n this.analyticsDebugConfig = analyticsDebugConfig;\n }\n\n //#region Console API\n log(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.log(message, optionalParams); //eslint-disable-line no-console\n }\n\n table(tabularData: unknown, properties?: readonly string[]) {\n if (!this.enabled) {\n return;\n }\n console.table(tabularData, properties); //eslint-disable-line no-console\n }\n\n warn(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.warn(message, optionalParams); //eslint-disable-line no-console\n }\n\n error(message?: unknown, ...optionalParams: unknown[]) {\n if (!this.enabled) {\n return;\n }\n console.error(message, optionalParams); //eslint-disable-line no-console\n }\n\n /**\n * Outputs an error message to user/customer console.\n *\n * Does not relay on {@link Logger#enabled}! because it should deliver the error information to user/customer.\n */\n errorMessageToUser(message?: unknown, ...optionalParams: unknown[]) {\n console.error(message, ...optionalParams); //eslint-disable-line no-console\n }\n //#endregion\n\n /** `true` if {@link AnalyticsConfig#debug} was set */\n private get enabled() {\n return (this.analyticsDebugConfig as boolean) || false;\n }\n}\n\nexport const padRight = (str: string | undefined, length: number) => {\n const padStr = new Array(length).join(' ');\n return (str + padStr).slice(0, length);\n};\n\nexport const logger = Logger.getInstance();\n","import type {InternalAdapterAPI} from '../adapters/internal/InternalAdapterAPI';\nimport type {Analytics} from '../core/Analytics';\n\nimport {logger} from './Logger';\nimport {isNullish} from './Utils';\n\nexport const BITMOVIN_ANALYTICS_AUGMENTED_MARKER = '__bitmovinAnalyticsHasBeenSetup';\n\n/**\n * Checks if analytics has already been initialized on this player instance,\n * aka. if {@link BITMOVIN_ANALYTICS_AUGMENTED_MARKER} is present on the player instance.\n *\n * @param player\n */\nexport function hasPlayerAlreadyBeenAugmented(player: any): boolean {\n return player[BITMOVIN_ANALYTICS_AUGMENTED_MARKER] === true;\n}\n\n/**\n * Marks the player instance as already instrumented by analytics,\n * aka. sets {@link BITMOVIN_ANALYTICS_AUGMENTED_MARKER} on the player instance.\n */\nexport function markPlayerInstanceAsAugmented(player: any) {\n player[BITMOVIN_ANALYTICS_AUGMENTED_MARKER] = true;\n}\n\n/**\n * In context of player augmentation, if player was already augmented, adapter properties\n * {@link Analytics} or {@link InternalAdapterAPI} will stay `undefined`, this type guard\n * is utility to help us check if the instance is defined.\n */\nexport function isDefined<T extends Analytics | InternalAdapterAPI>(instance: T | null | undefined): instance is T {\n if (isNullish(instance)) {\n logger.log(\"Bitmovin Analytics: Adapter hasn't been initialized yet\");\n return false;\n }\n\n return true;\n}\n","import {endsWith} from '../utils/stringUtils';\n\nexport const MIMETypes = {\n MP4: 'video/mp4',\n WEBM: 'video/webm',\n HLS: 'application/x-mpegURL',\n DASH: 'application/dash+xml',\n} as const;\n\n/**\n * @deprecated use {@link getStreamTypesFromURL} directly, when we want to detect {@link StreamTypes} from URL\n *\n * @remarks\n *\n * In our current code, it is visible that detection of MIME Type is only used as \"an additional step\" between\n * stream URL and stream type:\n * - we parse stream URL to detect MIME type\n * - we parse the detected MIME type to get a stream type\n *\n * Because we are not sending the detected MIME type in sample and because we can get {@link StreamTypes} directly from\n * stream URL, we should stop using this MIME type detection code.\n */\nexport function getMIMETypeFromFileExtension(url: string): string | undefined {\n const urlPath = url.split(/[?#]/)[0].toLowerCase();\n\n if (endsWith(urlPath, '.m3u8')) {\n return MIMETypes.HLS;\n }\n if (endsWith(urlPath, '.mp4') || endsWith(urlPath, '.m4v') || endsWith(urlPath, '.m4a')) {\n return MIMETypes.MP4;\n }\n if (endsWith(urlPath, '.webm')) {\n return MIMETypes.WEBM;\n }\n if (endsWith(urlPath, '.mpd')) {\n return MIMETypes.DASH;\n }\n\n return undefined;\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\n\nimport {Backend} from './Backend';\n\n/**\n * The `NoOpBackend` is a no-operation implementation of the `Backend` interface.\n * It serves as a placeholder backend when the actual `Backend` functionality is disabled or not required.\n * E.g. in scenarios such as releasing the adapter or when the Collector is disabled via {@link CollectorConfig#enabled}.\n *\n * Using `NoOpBackend` ensures that the code does not need to handle cases where `Backend` might be undefined,\n * thereby simplifying the logic and reducing the need for null or undefined checks.\n *\n * @implements {Backend}\n */\nexport class NoOpBackend implements Backend {\n sendRequest(_sample: Sample) {\n // empty\n }\n sendUnloadRequest(_sample: Sample) {\n // empty\n }\n sendRequestSynchronous(_sample: Sample) {\n // empty\n }\n sendAdRequest(_sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n // empty\n }\n}\n","import type {\n AnalyticsEventBase,\n AudioChangeEvent,\n CustomDataValuesEvent,\n ErrorEvent,\n SourceChangeEvent,\n VideoChangeEvent,\n} from '../types/EventData';\n\n/**\n * If we specify the name of our initial state, then an implicit 'startup' initial event will be created by JSM\n * and fired when the state machine is constructed.\n *\n * Because that implicit JSM initial event is called 'startup', it could cause confusion with our \"STARTUP state\", so for\n * that reason we will use custom JSM initial event name, to be able to distinguish it from our other {@link Event}s.\n *\n * This event should not be used in the application code, it is only used by the JSM library!\n *\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#initialization-options\n */\nexport const JSM_INITIAL_EVENT = 'jsm-initial';\n\nexport enum Event {\n AUDIO_CHANGE = 'audioChange',\n AUDIOTRACK_CHANGED = 'audioTrackChanged',\n CUSTOM_DATA_CHANGE = 'customDataChange',\n /**\n * Fired when the player has finished playback.\n */\n END = 'end',\n END_AD = 'adEnd',\n END_BUFFERING = 'endBuffering',\n END_CAST = 'endCasting',\n END_FULLSCREEN = 'endFullscreen',\n ERROR = 'playerError',\n MANUAL_SOURCE_CHANGE = 'manualSourceChangeInitiated',\n MUTE = 'mute',\n PAUSE = 'pause',\n PLAY = 'play',\n PLAYING = 'playing',\n /**\n * Fired when the player is ready to play.\n */\n READY = 'ready',\n SCREEN_RESIZE = 'resize',\n SEEK = 'seek',\n SEEKED = 'seeked',\n SOURCE_LOADED = 'sourceLoaded',\n SOURCE_UNLOADED = 'sourceUnloaded',\n START_AD = 'adStart',\n START_BUFFERING = 'startBuffering',\n START_CAST = 'startCasting',\n START_FULLSCREEN = 'startFullscreen',\n SUBTITLE_CHANGE = 'subtitleChange',\n TIMECHANGED = 'timechanged',\n UN_MUTE = 'unMute',\n /**\n * Fired when page with player is closed or when the player is unloaded/destroyed.\n */\n UNLOAD = 'unload',\n VIDEO_CHANGE = 'videoChange',\n VIDEOSTART_TIMEOUT = 'VIDEOSTART_TIMEOUT',\n}\n\nexport interface EventMap {\n [Event.READY]: AnalyticsEventBase;\n [Event.SOURCE_LOADED]: AnalyticsEventBase;\n [Event.PLAY]: AnalyticsEventBase;\n [Event.PLAYING]: AnalyticsEventBase | CustomDataValuesEvent;\n [Event.PAUSE]: AnalyticsEventBase | CustomDataValuesEvent;\n [Event.TIMECHANGED]: AnalyticsEventBase;\n [Event.SEEK]: AnalyticsEventBase;\n [Event.SEEKED]: AnalyticsEventBase;\n [Event.START_CAST]: AnalyticsEventBase;\n [Event.END_CAST]: AnalyticsEventBase;\n [Event.START_BUFFERING]: AnalyticsEventBase;\n [Event.END_BUFFERING]: AnalyticsEventBase;\n [Event.AUDIOTRACK_CHANGED]: AnalyticsEventBase;\n [Event.AUDIO_CHANGE]: AudioChangeEvent;\n [Event.VIDEO_CHANGE]: VideoChangeEvent;\n [Event.START_FULLSCREEN]: AnalyticsEventBase;\n [Event.END_FULLSCREEN]: AnalyticsEventBase;\n [Event.START_AD]: AnalyticsEventBase;\n [Event.SUBTITLE_CHANGE]: AnalyticsEventBase;\n [Event.END_AD]: AnalyticsEventBase;\n [Event.MUTE]: AnalyticsEventBase;\n [Event.UN_MUTE]: AnalyticsEventBase;\n [Event.ERROR]: ErrorEvent;\n [Event.SCREEN_RESIZE]: AnalyticsEventBase;\n [Event.UNLOAD]: AnalyticsEventBase;\n [Event.END]: AnalyticsEventBase;\n [Event.SOURCE_UNLOADED]: AnalyticsEventBase;\n [Event.MANUAL_SOURCE_CHANGE]: SourceChangeEvent;\n [Event.VIDEOSTART_TIMEOUT]: AnalyticsEventBase;\n [Event.CUSTOM_DATA_CHANGE]: AnalyticsEventBase;\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {AnalyticsCall} from '../utils/AnalyticsCall';\nimport {noOp} from '../utils/Utils';\n\nimport {Backend} from './Backend';\n\n/**\n * The `RemoteBackend` class is responsible for actually sending out the samples using the {@link AnalyticsCall} class.\n * Before each sample is sent, the `RemoteBackend` attaches a license key to the sample.\n *\n * @implements {Backend}\n */\nexport class RemoteBackend implements Backend {\n analyticsCall: AnalyticsCall;\n hasAdModule: boolean;\n\n constructor(\n hasAdModule: boolean,\n backendBaseUrl: string,\n private licenseKey: string,\n ) {\n this.hasAdModule = hasAdModule;\n this.analyticsCall = new AnalyticsCall(backendBaseUrl);\n }\n\n sendRequest(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendRequest(sample, noOp);\n }\n\n sendUnloadRequest(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n sample.key = this.licenseKey;\n this.analyticsCall.sendRequestSynchronous(sample, noOp);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n sample.key = this.licenseKey;\n if (!this.hasAdModule) {\n return;\n }\n this.analyticsCall.sendAdRequest(sample);\n }\n}\n","interface EventListener {\n eventName: string;\n func: EventListenerOrEventListenerObject;\n}\n\nexport class WindowEventTracker {\n private trackedObjects: EventListener[] = [];\n\n addEventListener(eventName: string, func: EventListenerOrEventListenerObject) {\n this.trackedObjects.push({eventName, func});\n window.addEventListener(eventName, func);\n }\n\n release() {\n while (this.trackedObjects.length !== 0) {\n const obj = this.trackedObjects.pop();\n if (obj === undefined) {\n continue;\n }\n\n window.removeEventListener(obj.eventName, obj.func);\n }\n }\n}\n","import * as StateMachine from 'javascript-state-machine';\n\nimport {HeartbeatService} from '../../core/HeartbeatService';\nimport {Event, JSM_INITIAL_EVENT} from '../../enums/Event';\nimport {createVideoStartFailedReason} from '../../enums/VideoStartFailedReason';\nimport type {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {AnalyticsEventBase, ErrorEvent} from '../../types/EventData';\nimport type {StateMachineCallbacks} from '../../types/StateMachineCallbacks';\nimport {EventDebugging} from '../../utils/EventDebugging';\nimport {logger} from '../../utils/Logger';\nimport {isNotNullish, isNumber, noOp} from '../../utils/Utils';\nimport {AnalyticsStateMachine} from '../AnalyticsStateMachine';\nimport {\n customStateMachineErrorCallback,\n logMissingCallbackWarning,\n logStateMachineTransition,\n on,\n} from '../stateMachineUtils';\n\nenum State {\n AD_PAUSE = 'AD_PAUSE',\n AD_PLAYING = 'AD_PLAYING',\n AD_READY = 'AD_READY',\n /** This event is called when an ad is played directly after the player startup phase */\n AD_STARTUP = 'AD_STARTUP',\n AUDIOTRACK_CHANGING = 'AUDIOTRACK_CHANGING',\n CASTING = 'CASTING',\n /**\n * This state was created only to be able to \"cut\" the {@link State.PLAYING} and {@link State.PAUSE}\n * and send playing/pause sample with current custom data, while calling {@link AdapterAPI.setCustomData} function\n * and setting the new custom data values.\n *\n * @remarks\n *\n * Our implementation relays on a specific state name \"CUSTOMDATACHANGE\" because it should call the\n * default \"onleavestate\" state machine callback {@link stateMachineCallbacks.customdatachange}.\n */\n CUSTOMDATACHANGE = 'CUSTOMDATACHANGE',\n END = 'END',\n /** see {@link State.PLAY_SEEKING} */\n END_PLAY_SEEKING = 'END_PLAY_SEEKING',\n ERROR = 'ERROR',\n INITIAL_SOURCE_CHANGE = 'INITIAL_SOURCE_CHANGE',\n MUTING_PAUSE = 'MUTING_PAUSE',\n MUTING_PLAY = 'MUTING_PLAY',\n MUTING_READY = 'MUTING_READY',\n PAUSE = 'PAUSE',\n /**\n * THE Seeking state.\n * Seeking tracking = time spend in PLAY_SEEKING + END_PLAY_SEEKING.\n * - PLAY_SEEKING - THE seeking state for tracking time spend in seeking.\n * - END_PLAY_SEEKING - part of seeking time, where we wait `in between` seeking and continuing with other states.\n * - usually we are in this state when holding the mouse while seeking -> this will produce multiple connected seeks.\n */\n PLAY_SEEKING = 'PLAY_SEEKING',\n PLAYING = 'PLAYING',\n QUALITYCHANGE = 'QUALITYCHANGE',\n QUALITYCHANGE_PAUSE = 'QUALITYCHANGE_PAUSE',\n QUALITYCHANGE_REBUFFERING = 'QUALITYCHANGE_REBUFFERING',\n READY = 'READY',\n REBUFFERING = 'REBUFFERING',\n SETUP = 'SETUP',\n SOURCE_CHANGING = 'SOURCE_CHANGING',\n STARTUP = 'STARTUP',\n SUBTITLE_CHANGING = 'SUBTITLE_CHANGING',\n VIDEOSTART_FAILED = 'VIDEOSTART_FAILED',\n}\n\nexport class Bitmovin8AnalyticsStateMachine extends AnalyticsStateMachine {\n private debuggingStates: EventDebugging[] = [];\n private enabledDebugging = false;\n\n private seekStartTimestamp: number | undefined;\n /**\n * Used for ads, because when AdFinished event is fired and a call to state machine is made,\n * data from player indicate that video is playing from beginning even if ad is in the middle of video\n */\n private lastTrackedVideoEndObject?: AnalyticsEventBase;\n\n constructor(\n stateMachineCallbacks: StateMachineCallbacks,\n playingHeartbeatService: HeartbeatService,\n opts: AnalyticsStateMachineOptions,\n ) {\n super(stateMachineCallbacks, playingHeartbeatService, opts);\n }\n\n getAllStatesBut(states: string[]) {\n return this.getAllStates().filter((i) => states.indexOf(i) < 0);\n }\n\n getAllStates() {\n return Object.keys(State).map((key) => State[key]);\n }\n\n override createStateMachine(opts: AnalyticsStateMachineOptions): StateMachine.StateMachine {\n return StateMachine.create({\n // custom initial state and custom JSM initial event name\n // initial event is used by JSM for the initial state transition 'none' -> 'SETUP'\n initial: {state: State.SETUP, event: JSM_INITIAL_EVENT},\n error: customStateMachineErrorCallback,\n events: [\n {\n name: Event.SOURCE_LOADED,\n from: [State.SETUP, State.ERROR, State.SOURCE_CHANGING, State.INITIAL_SOURCE_CHANGE],\n to: State.READY,\n },\n\n {name: Event.PLAY, from: State.READY, to: State.STARTUP},\n {name: Event.PLAYING, from: State.READY, to: State.PLAYING},\n on(Event.READY).stayIn(State.READY),\n on(Event.VIDEO_CHANGE).stayIn(State.READY),\n on(Event.AUDIO_CHANGE).stayIn(State.READY),\n\n {name: Event.ERROR, from: [State.STARTUP, State.AD_STARTUP], to: State.VIDEOSTART_FAILED},\n {name: Event.UNLOAD, from: [State.STARTUP, State.AD_STARTUP], to: State.VIDEOSTART_FAILED},\n {name: Event.VIDEOSTART_TIMEOUT, from: State.STARTUP, to: State.VIDEOSTART_FAILED},\n\n on(Event.PLAY).stayIn(State.STARTUP),\n on(Event.PLAYING).stayIn(State.STARTUP),\n {name: Event.TIMECHANGED, from: State.STARTUP, to: State.PLAYING},\n on(Event.START_BUFFERING).stayIn(State.STARTUP),\n on(Event.END_BUFFERING).stayIn(State.STARTUP),\n on(Event.VIDEO_CHANGE).stayIn(State.STARTUP),\n on(Event.AUDIO_CHANGE).stayIn(State.STARTUP),\n on(Event.READY).stayIn(State.STARTUP),\n {name: Event.PAUSE, from: State.STARTUP, to: State.READY},\n\n on(Event.PLAYING).stayIn(State.PLAYING),\n on(Event.TIMECHANGED).stayIn(State.PLAYING),\n on(Event.END_BUFFERING).stayIn(State.PLAYING),\n {name: Event.START_BUFFERING, from: State.PLAYING, to: State.REBUFFERING},\n {name: Event.END_BUFFERING, from: State.REBUFFERING, to: State.PLAYING},\n on(Event.TIMECHANGED).stayIn(State.REBUFFERING),\n\n {name: Event.PAUSE, from: State.PLAYING, to: State.PAUSE},\n {name: Event.PAUSE, from: State.REBUFFERING, to: State.PAUSE},\n {name: Event.PLAY, from: State.PAUSE, to: State.PLAYING},\n\n {name: Event.VIDEO_CHANGE, from: State.PLAYING, to: State.QUALITYCHANGE},\n {name: Event.AUDIO_CHANGE, from: State.PLAYING, to: State.QUALITYCHANGE},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE),\n {name: 'FINISH_QUALITYCHANGE', from: State.QUALITYCHANGE, to: State.PLAYING},\n\n {name: Event.VIDEO_CHANGE, from: State.PAUSE, to: State.QUALITYCHANGE_PAUSE},\n {name: Event.AUDIO_CHANGE, from: State.PAUSE, to: State.QUALITYCHANGE_PAUSE},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE_PAUSE),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE_PAUSE),\n {name: 'FINISH_QUALITYCHANGE_PAUSE', from: State.QUALITYCHANGE_PAUSE, to: State.PAUSE},\n\n //#region Seeking\n\n // start seeking\n {name: Event.SEEK, from: State.PLAYING, to: State.PLAY_SEEKING},\n\n // mark the seeked as finished\n {name: Event.PLAY, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n {name: Event.PLAYING, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n {name: Event.SEEKED, from: State.PLAY_SEEKING, to: State.END_PLAY_SEEKING},\n\n // seek while previous seek not completed\n {name: Event.SEEK, from: State.END_PLAY_SEEKING, to: State.PLAY_SEEKING},\n\n // seek completely finished and cont playing\n {name: Event.PLAYING, from: State.END_PLAY_SEEKING, to: State.PLAYING},\n {name: Event.TIMECHANGED, from: State.END_PLAY_SEEKING, to: State.PLAYING},\n\n // if PAUSE happens during the seeking (or at the end of seeking) we need to transition to PAUSE state\n {name: Event.PAUSE, from: [State.PLAY_SEEKING, State.END_PLAY_SEEKING], to: State.PAUSE},\n\n //#region Seeking disabled transitions\n // ignore transitions in PLAY_SEEKING\n on(Event.SEEK).stayIn(State.PLAY_SEEKING),\n on(Event.AUDIO_CHANGE).stayIn(State.PLAY_SEEKING),\n on(Event.VIDEO_CHANGE).stayIn(State.PLAY_SEEKING),\n on(Event.START_BUFFERING).stayIn(State.PLAY_SEEKING),\n on(Event.END_BUFFERING).stayIn(State.PLAY_SEEKING),\n\n // ignore transitions in END_PLAY_SEEKING\n on(Event.START_BUFFERING).stayIn(State.END_PLAY_SEEKING),\n on(Event.END_BUFFERING).stayIn(State.END_PLAY_SEEKING),\n on(Event.SEEKED).stayIn(State.END_PLAY_SEEKING),\n on(Event.PLAY).stayIn(State.END_PLAY_SEEKING),\n\n // ignore Seek events during PAUSE\n on(Event.SEEK).stayIn(State.PAUSE),\n on(Event.SEEKED).stayIn(State.PAUSE),\n\n // ignore seeked during Playing because of not allowed keyboard seeking\n on(Event.SEEKED).stayIn(State.PLAYING),\n //#endregion Seeking disabled transitions\n\n //#endregion Seeking\n\n {name: Event.END, from: State.PLAY_SEEKING, to: State.END},\n {name: Event.END, from: State.PLAYING, to: State.END},\n {name: Event.END, from: State.PAUSE, to: State.END},\n\n on(Event.SEEK).stayIn(State.END),\n on(Event.SEEKED).stayIn(State.END),\n on(Event.TIMECHANGED).stayIn(State.END),\n on(Event.END_BUFFERING).stayIn(State.END),\n on(Event.START_BUFFERING).stayIn(State.END),\n on(Event.END).stayIn(State.END),\n\n {name: Event.PLAY, from: State.END, to: State.STARTUP},\n\n {name: Event.ERROR, from: this.getAllStatesBut([State.STARTUP]), to: State.ERROR},\n\n {name: Event.UNLOAD, from: this.getAllStatesBut([State.STARTUP, State.AD_STARTUP]), to: State.END},\n\n {name: Event.SUBTITLE_CHANGE, from: State.PLAYING, to: State.SUBTITLE_CHANGING},\n on(Event.SUBTITLE_CHANGE).stayIn(State.PAUSE),\n on(Event.SUBTITLE_CHANGE).stayIn(State.REBUFFERING),\n on(Event.SUBTITLE_CHANGE).stayIn(State.END_PLAY_SEEKING),\n on(Event.SUBTITLE_CHANGE).stayIn(State.SUBTITLE_CHANGING),\n {name: Event.TIMECHANGED, from: State.SUBTITLE_CHANGING, to: State.PLAYING},\n\n {name: Event.AUDIOTRACK_CHANGED, from: State.PLAYING, to: State.AUDIOTRACK_CHANGING},\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.PAUSE),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.REBUFFERING),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.END_PLAY_SEEKING),\n on(Event.AUDIOTRACK_CHANGED).stayIn(State.AUDIOTRACK_CHANGING),\n {name: Event.TIMECHANGED, from: State.AUDIOTRACK_CHANGING, to: State.PLAYING},\n\n // #region Ads\n {name: Event.START_AD, from: State.STARTUP, to: State.AD_STARTUP},\n {name: Event.END_AD, from: State.AD_STARTUP, to: State.STARTUP},\n on(Event.PLAY).stayIn(State.AD_STARTUP),\n on(Event.PAUSE).stayIn(State.AD_STARTUP),\n\n {name: Event.START_AD, from: State.READY, to: State.AD_READY},\n /** After the pre-rolls, the main content will always start playing, no matter if autoplay: true/false */\n {name: Event.END_AD, from: State.AD_READY, to: State.STARTUP},\n on(Event.PLAY).stayIn(State.AD_READY),\n on(Event.PAUSE).stayIn(State.AD_READY),\n\n {name: Event.START_AD, from: State.PAUSE, to: State.AD_PAUSE},\n {name: Event.END_AD, from: State.AD_PAUSE, to: State.PAUSE},\n on(Event.PLAY).stayIn(State.AD_PAUSE),\n on(Event.PAUSE).stayIn(State.AD_PAUSE),\n\n {name: Event.START_AD, from: State.PLAYING, to: State.AD_PLAYING},\n {name: Event.END_AD, from: State.AD_PLAYING, to: State.PLAYING},\n on(Event.PLAY).stayIn(State.AD_PLAYING),\n on(Event.PAUSE).stayIn(State.AD_PLAYING),\n {name: Event.END, from: State.AD_PLAYING, to: State.END},\n\n // Ignore timechanged events during ads\n on(Event.TIMECHANGED).stayIn(State.AD_STARTUP),\n on(Event.TIMECHANGED).stayIn(State.AD_READY),\n on(Event.TIMECHANGED).stayIn(State.AD_PAUSE),\n on(Event.TIMECHANGED).stayIn(State.AD_PLAYING),\n\n // Ignore End Ad events when no ad has started\n on(Event.END_AD).stayIn(State.PLAYING),\n on(Event.END_AD).stayIn(State.PAUSE),\n on(Event.END_AD).stayIn(State.READY),\n on(Event.END_AD).stayIn(State.STARTUP),\n // #endregion\n\n {name: Event.MUTE, from: State.READY, to: State.MUTING_READY},\n {name: Event.UN_MUTE, from: State.READY, to: State.MUTING_READY},\n {name: 'FINISH_MUTING', from: State.MUTING_READY, to: State.READY},\n\n {name: Event.MUTE, from: State.PLAYING, to: State.MUTING_PLAY},\n {name: Event.UN_MUTE, from: State.PLAYING, to: State.MUTING_PLAY},\n {name: 'FINISH_MUTING', from: State.MUTING_PLAY, to: State.PLAYING},\n\n {name: Event.MUTE, from: State.PAUSE, to: State.MUTING_PAUSE},\n {name: Event.UN_MUTE, from: State.PAUSE, to: State.MUTING_PAUSE},\n {name: 'FINISH_MUTING', from: State.MUTING_PAUSE, to: State.PAUSE},\n\n {name: Event.START_CAST, from: [State.READY, State.PAUSE, State.PLAYING], to: State.CASTING},\n on(Event.PAUSE).stayIn(State.CASTING),\n on(Event.PLAY).stayIn(State.CASTING),\n on(Event.PLAYING).stayIn(State.CASTING),\n on(Event.TIMECHANGED).stayIn(State.CASTING),\n on(Event.MUTE).stayIn(State.CASTING),\n on(Event.UN_MUTE).stayIn(State.CASTING),\n on(Event.SEEK).stayIn(State.CASTING),\n on(Event.SEEKED).stayIn(State.CASTING),\n {name: Event.END_CAST, from: State.CASTING, to: State.READY},\n\n on(Event.SEEK).stayIn(State.READY),\n on(Event.SEEKED).stayIn(State.READY),\n on(Event.SEEKED).stayIn(State.STARTUP),\n\n {name: Event.MANUAL_SOURCE_CHANGE, from: this.getAllStatesBut([State.SETUP]), to: State.SOURCE_CHANGING},\n {name: Event.MANUAL_SOURCE_CHANGE, from: State.SETUP, to: State.INITIAL_SOURCE_CHANGE},\n {name: Event.SOURCE_UNLOADED, from: this.getAllStates(), to: State.SOURCE_CHANGING},\n\n // {name: Event.READY, from: State.SOURCE_CHANGING, to: State.READY},\n\n {name: Event.VIDEO_CHANGE, from: State.REBUFFERING, to: State.QUALITYCHANGE_REBUFFERING},\n {name: Event.AUDIO_CHANGE, from: State.REBUFFERING, to: State.QUALITYCHANGE_REBUFFERING},\n on(Event.VIDEO_CHANGE).stayIn(State.QUALITYCHANGE_REBUFFERING),\n on(Event.AUDIO_CHANGE).stayIn(State.QUALITYCHANGE_REBUFFERING),\n {name: 'FINISH_QUALITYCHANGE_REBUFFERING', from: State.QUALITYCHANGE_REBUFFERING, to: State.REBUFFERING},\n\n // Because of this state transition, we are able to male \"a cut\" in the current PLAYING / PAUSE state\n // and send \"playing\" / \"pause\" sample with the current custom data values. The new changed custom data values\n // will be set on upcoming samples after we transition back from the CUSTOMDATACHANGE state.\n // For any other states, we don't care, because InternalAdapter is not emitting the event.\n {name: Event.CUSTOM_DATA_CHANGE, from: [State.PLAYING, State.PAUSE], to: State.CUSTOMDATACHANGE},\n {name: Event.PLAYING, from: State.CUSTOMDATACHANGE, to: State.PLAYING},\n {name: Event.PAUSE, from: State.CUSTOMDATACHANGE, to: State.PAUSE},\n ],\n\n // Keep callbacks sorted by order in which they are called by JSM library (and after order, sorted by name)\n //\n // Do not use convenience, shortened callbacks\n // - instead of `onEVENT` use `onafterEVENT`\n // - instead of `onSTATE` use `onenterSTATE`\n //\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#callbacks\n callbacks: {\n onbeforeevent: (_event, from, to, _eventTimestamp: number, _eventData: AnalyticsEventBase): any => {\n if (from === State.REBUFFERING && to === State.QUALITYCHANGE_REBUFFERING) {\n // return false from an `onbeforeEVENT` handler to cancel the event.\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#callbacks\n //\n // Svarozic (2025-06-18):\n // Not sure if this works as expected because, according to DOCS (as far as I understand),\n // it should be in specific event callback `onbefore${EVENT_NAME}`\n return false;\n }\n },\n\n [`onleave${State.END_PLAY_SEEKING}`]: (\n _event,\n _from,\n to,\n eventTimestamp: number,\n eventData: AnalyticsEventBase,\n ) => {\n if (to === State.PLAY_SEEKING) {\n // seeking is not finished yet, do not send \"seeking\" sample\n return;\n }\n\n // seeking has finished / was interrupted - send out seeking sample\n const seekDuration = eventTimestamp - (this.seekStartTimestamp ?? eventTimestamp);\n this.seekStartTimestamp = undefined;\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventData);\n this.stateMachineCallbacks.end_play_seeking(seekDuration, 'end_play_seeking');\n },\n\n [`onleave${State.PLAYING}`]: () => {\n this.playingHeartbeatService.stopHeartbeat();\n },\n\n [`onleave${State.PLAY_SEEKING}`]: (_event, _from, to, eventTimestamp: number, _eventData) => {\n if (to === State.END_PLAY_SEEKING) {\n // regular seek workflow preparing to end seeking\n return;\n }\n\n // seek interrupted - not regular exit of seeking\n const seekDuration = eventTimestamp - (this.seekStartTimestamp ?? eventTimestamp);\n this.seekStartTimestamp = undefined;\n // we are using here state name `end_play_seeking` to not introduce another state to our database\n this.stateMachineCallbacks.end_play_seeking(seekDuration, 'end_play_seeking');\n },\n\n onleavestate: (event, from, to, eventTimestamp, eventData: AnalyticsEventBase) => {\n logStateMachineTransition('LEAVE', event, from, to);\n\n // Skip this JSM callback for JSM initial event\n // This event is fired when the state machine is constructed,\n // to transition us from 'none' to custom initial 'SETUP' state\n if (event === JSM_INITIAL_EVENT) {\n return;\n }\n\n if (from === State.REBUFFERING) {\n this.resetRebufferingHelpers();\n }\n\n // Skip this JSM callback when an JSM event without a timestamp is called,\n // because it would cause NPE in analytics code (state duration calculation etc.).\n // This probably has happened because the state machine was not used correctly,\n // aka. JSM event was not called via `callEvent` method as it should be!\n if (!eventTimestamp) {\n return;\n }\n\n this.addStatesToLog(event, from, to, eventTimestamp, eventData);\n const stateDuration = eventTimestamp - this.onEnterStateTimestamp;\n\n if (eventData && to !== State.END_PLAY_SEEKING) {\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventData);\n }\n\n if (eventData && event !== Event.END_AD) {\n this.lastTrackedVideoEndObject = eventData;\n }\n\n if ((from === State.READY || from === State.AD_STARTUP) && to === State.STARTUP) {\n this.setVideoStartTimeout();\n } else if (from === State.STARTUP && (to === State.PLAYING || to === State.AD_STARTUP)) {\n this.clearVideoStartTimeout();\n }\n\n const lowerCaseFrom = String(from).toLowerCase();\n if (to === State.VIDEOSTART_FAILED) {\n this.clearVideoStartTimeout();\n this.stateMachineCallbacks.videoStartFailed(stateDuration, createVideoStartFailedReason(event));\n } else if (from === State.END_PLAY_SEEKING) {\n // NOOP - skip last else block to not send sample\n // sending of sample is handled in `on Leave Seeking` state transition handler\n noOp();\n } else if (event === Event.UNLOAD) {\n this.stateMachineCallbacks.unload(stateDuration, lowerCaseFrom);\n } else if (\n from === State.AD_PAUSE ||\n from === State.AD_READY ||\n from === State.AD_PLAYING ||\n from === State.AD_STARTUP\n ) {\n if (isNotNullish(this.lastTrackedVideoEndObject)) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(this.lastTrackedVideoEndObject);\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(this.lastTrackedVideoEndObject);\n }\n this.stateMachineCallbacks.ad(stateDuration, 'ad');\n } else if (event === Event.START_AD && from === State.STARTUP) {\n noOp();\n } else if (event === Event.SOURCE_LOADED && from === State.INITIAL_SOURCE_CHANGE) {\n noOp();\n } else if (from === State.SETUP) {\n // Setting Player Startup Time to fixed value of 1ms.\n // We can not get correct Player Startup Time from bitmovin player, because it does not have an \"onInitialized\" event\n this.stateMachineCallbacks.setup(1, State.SETUP.toLowerCase());\n } else if (event === Event.PAUSE && from === State.STARTUP && to === State.READY) {\n // fired PAUSE event in STARTUP state indicates we are moving back to READY,\n // so we have to clean setTimeout, and we should not call any stateMachineCallbacks\n this.clearVideoStartTimeout();\n } else if (from !== State.ERROR) {\n // Default \"onleavestate\" state machine callback\n //\n // Every time, when we leave a state, we should try to call \"state\" callback,\n // to be able to make \"a cut\" and send analytics sample (if necessary)\n const defaultStateMachineCallbackFn = this.stateMachineCallbacks[lowerCaseFrom];\n if (typeof defaultStateMachineCallbackFn === 'function') {\n // a try-catch block to add more resilience against callback errors\n try {\n defaultStateMachineCallbackFn(stateDuration, lowerCaseFrom, eventData);\n } catch (e) {\n logger.error('Exception occurred in State Machine callback ' + lowerCaseFrom, eventData, e);\n }\n } else {\n // if callback is not defined, log a warning to indicate to the developer that\n // - a new callback function needs to be implemented to relay on this default state machine callback\n // - or if no callback is needed, we should\n // - early return from this JSM callback\n // - or add this state to the ignored list\n logMissingCallbackWarning(from, [State.READY, State.SOURCE_CHANGING]);\n }\n }\n\n if (\n eventData &&\n to !== State.END_PLAY_SEEKING &&\n from !== State.PLAY_SEEKING &&\n to !== State.PLAY_SEEKING &&\n from !== State.AD_STARTUP &&\n from !== State.AD_READY &&\n from !== State.AD_PLAYING &&\n from !== State.AD_PAUSE\n ) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventData);\n }\n\n if (event === Event.VIDEO_CHANGE) {\n this.stateMachineCallbacks.videoChange(eventData);\n } else if (event === Event.AUDIO_CHANGE) {\n this.stateMachineCallbacks.audioChange(eventData);\n } else if (event === Event.MUTE) {\n this.stateMachineCallbacks.mute();\n } else if (event === Event.UN_MUTE) {\n this.stateMachineCallbacks.unMute();\n }\n },\n\n [`onenter${State.PLAYING}`]: () => {\n this.playingHeartbeatService.startHeartbeat();\n },\n\n [`onenter${State.PLAY_SEEKING}`]: (event, from, _to, eventTimestamp: number, _eventData) => {\n if (from === State.END_PLAY_SEEKING) {\n // no start of seeking -> continues to seek and we don't need to have seek start timestamp\n return;\n }\n\n this.seekStartTimestamp = eventTimestamp;\n },\n\n onenterstate: (event, from, to, eventTimestamp: number, eventData: AnalyticsEventBase) => {\n logStateMachineTransition('ENTER', event, from, to);\n\n this.onEnterStateTimestamp = eventTimestamp ?? Date.now();\n // if customer set custom \"start time\" timestamp in AnalyticsStateMachineOptions of adapter constructor,\n // use it and override `onEnterStateTimestamp` during JSM initialization (transition to initial SETUP state)\n if (isNumber(opts.starttime) && event === JSM_INITIAL_EVENT) {\n this.onEnterStateTimestamp = opts.starttime;\n }\n\n if (\n eventData &&\n to !== State.END_PLAY_SEEKING &&\n from !== State.PLAY_SEEKING &&\n from !== State.AD_STARTUP &&\n from !== State.AD_READY &&\n from !== State.AD_PLAYING &&\n from !== State.AD_PAUSE &&\n !(event === Event.SEEK && from === State.END_PLAY_SEEKING)\n ) {\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventData);\n }\n\n if (event === Event.START_CAST && to === State.CASTING) {\n this.stateMachineCallbacks.startCasting(eventTimestamp, eventData);\n }\n\n if (to === State.REBUFFERING) {\n this.startRebufferingHeartbeatInterval();\n }\n },\n\n [`onafter${Event.ERROR}`]: (_event, _from, _to, _eventTimestamp, eventData: ErrorEvent) => {\n this.stateMachineCallbacks.error(eventData);\n },\n\n onafterevent: (event, from, to, eventTimestamp: number, eventData) => {\n if (event === Event.MANUAL_SOURCE_CHANGE && from === State.SETUP) {\n this.stateMachineCallbacks.initialSourceChange(eventData);\n } else if (event === Event.MANUAL_SOURCE_CHANGE) {\n this.stateMachineCallbacks.manualSourceChange(eventData);\n }\n\n if (to === State.QUALITYCHANGE_PAUSE) {\n this.stateMachine.FINISH_QUALITYCHANGE_PAUSE(eventTimestamp);\n }\n if (to === State.QUALITYCHANGE) {\n this.stateMachine.FINISH_QUALITYCHANGE(eventTimestamp);\n }\n if (to === State.QUALITYCHANGE_REBUFFERING) {\n this.stateMachine.FINISH_QUALITYCHANGE_REBUFFERING(eventTimestamp);\n }\n if (to === State.MUTING_READY || to === State.MUTING_PLAY || to === State.MUTING_PAUSE) {\n this.stateMachine.FINISH_MUTING(eventTimestamp);\n }\n },\n },\n });\n }\n\n override onSsaiPlaybackInteraction(timestamp: number, eventObject: AnalyticsEventBase) {\n // We don't allow this in any other state because it could interrupt the natural flow of the states\n // only PLAYING is considered a state which we can interrupt just like the heartbeat does\n // also we don't want to send samples with state we usually don't send samples like `ready`\n if (this.currentState != State.PLAYING) {\n return;\n }\n\n // Because ssai playback interaction can happen before Ssai Service is active (e.g. first ssai startAd call),\n // we need to manually mark sample as triggered by ssai\n //\n // This is also including the last sample marking, before a ssai ad block (due to ssai being spiky by design)\n this.sendPlayingSample(timestamp, eventObject, true);\n }\n\n getStates() {\n return this.debuggingStates;\n }\n\n setEnabledDebugging(enabled: boolean) {\n this.enabledDebugging = enabled;\n }\n\n private addStatesToLog(\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n timestamp: number,\n eventObject: any,\n ) {\n if (this.enabledDebugging) {\n this.debuggingStates.push(new EventDebugging(event, from, to, timestamp, eventObject));\n }\n }\n}\n","/*\n\n Javascript State Machine Library - https://github.com/jakesgordon/javascript-state-machine\n\n Copyright (c) 2012, 2013, 2014, 2015, Jake Gordon and contributors\n Released under the MIT license - https://github.com/jakesgordon/javascript-state-machine/blob/master/LICENSE\n\n*/\n\n(function () {\n\n var StateMachine = {\n\n //---------------------------------------------------------------------------\n\n VERSION: \"2.4.0\",\n\n //---------------------------------------------------------------------------\n\n Result: {\n SUCCEEDED: 1, // the event transitioned successfully from one state to another\n NOTRANSITION: 2, // the event was successfull but no state transition was necessary\n CANCELLED: 3, // the event was cancelled by the caller in a beforeEvent callback\n PENDING: 4 // the event is asynchronous and the caller is in control of when the transition occurs\n },\n\n Error: {\n INVALID_TRANSITION: 100, // caller tried to fire an event that was innapropriate in the current state\n PENDING_TRANSITION: 200, // caller tried to fire an event while an async transition was still pending\n INVALID_CALLBACK: 300 // caller provided callback function threw an exception\n },\n\n WILDCARD: '*',\n ASYNC: 'async',\n\n //---------------------------------------------------------------------------\n\n create: function(cfg, target) {\n\n var initial = (typeof cfg.initial == 'string') ? { state: cfg.initial } : cfg.initial; // allow for a simple string, or an object with { state: 'foo', event: 'setup', defer: true|false }\n var terminal = cfg.terminal || cfg['final'];\n var fsm = target || cfg.target || {};\n var events = cfg.events || [];\n var callbacks = cfg.callbacks || {};\n var map = {}; // track state transitions allowed for an event { event: { from: [ to ] } }\n var transitions = {}; // track events allowed from a state { state: [ event ] }\n\n var add = function(e) {\n var from = Array.isArray(e.from) ? e.from : (e.from ? [e.from] : [StateMachine.WILDCARD]); // allow 'wildcard' transition if 'from' is not specified\n map[e.name] = map[e.name] || {};\n for (var n = 0 ; n < from.length ; n++) {\n transitions[from[n]] = transitions[from[n]] || [];\n transitions[from[n]].push(e.name);\n\n map[e.name][from[n]] = e.to || from[n]; // allow no-op transition if 'to' is not specified\n }\n if (e.to)\n transitions[e.to] = transitions[e.to] || [];\n };\n\n if (initial) {\n initial.event = initial.event || 'startup';\n add({ name: initial.event, from: 'none', to: initial.state });\n }\n\n for(var n = 0 ; n < events.length ; n++)\n add(events[n]);\n\n for(var name in map) {\n if (map.hasOwnProperty(name))\n fsm[name] = StateMachine.buildEvent(name, map[name]);\n }\n\n for(var name in callbacks) {\n if (callbacks.hasOwnProperty(name))\n fsm[name] = callbacks[name]\n }\n\n fsm.current = 'none';\n fsm.is = function(state) { return Array.isArray(state) ? (state.indexOf(this.current) >= 0) : (this.current === state); };\n fsm.can = function(event) { return !this.transition && (map[event] !== undefined) && (map[event].hasOwnProperty(this.current) || map[event].hasOwnProperty(StateMachine.WILDCARD)); }\n fsm.cannot = function(event) { return !this.can(event); };\n fsm.transitions = function() { return (transitions[this.current] || []).concat(transitions[StateMachine.WILDCARD] || []); };\n fsm.isFinished = function() { return this.is(terminal); };\n fsm.error = cfg.error || function(name, from, to, args, error, msg, e) { throw e || msg; }; // default behavior when something unexpected happens is to throw an exception, but caller can override this behavior if desired (see github issue #3 and #17)\n fsm.states = function() { return Object.keys(transitions).sort() };\n\n if (initial && !initial.defer)\n fsm[initial.event]();\n\n return fsm;\n\n },\n\n //===========================================================================\n\n doCallback: function(fsm, func, name, from, to, args) {\n if (func) {\n try {\n return func.apply(fsm, [name, from, to].concat(args));\n }\n catch(e) {\n return fsm.error(name, from, to, args, StateMachine.Error.INVALID_CALLBACK, \"an exception occurred in a caller-provided callback function\", e);\n }\n }\n },\n\n beforeAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbeforeevent'], name, from, to, args); },\n afterAnyEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafterevent'] || fsm['onevent'], name, from, to, args); },\n leaveAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleavestate'], name, from, to, args); },\n enterAnyState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenterstate'] || fsm['onstate'], name, from, to, args); },\n changeState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onchangestate'], name, from, to, args); },\n\n beforeThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onbefore' + name], name, from, to, args); },\n afterThisEvent: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onafter' + name] || fsm['on' + name], name, from, to, args); },\n leaveThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onleave' + from], name, from, to, args); },\n enterThisState: function(fsm, name, from, to, args) { return StateMachine.doCallback(fsm, fsm['onenter' + to] || fsm['on' + to], name, from, to, args); },\n\n beforeEvent: function(fsm, name, from, to, args) {\n if ((false === StateMachine.beforeThisEvent(fsm, name, from, to, args)) ||\n (false === StateMachine.beforeAnyEvent( fsm, name, from, to, args)))\n return false;\n },\n\n afterEvent: function(fsm, name, from, to, args) {\n StateMachine.afterThisEvent(fsm, name, from, to, args);\n StateMachine.afterAnyEvent( fsm, name, from, to, args);\n },\n\n leaveState: function(fsm, name, from, to, args) {\n var specific = StateMachine.leaveThisState(fsm, name, from, to, args),\n general = StateMachine.leaveAnyState( fsm, name, from, to, args);\n if ((false === specific) || (false === general))\n return false;\n else if ((StateMachine.ASYNC === specific) || (StateMachine.ASYNC === general))\n return StateMachine.ASYNC;\n },\n\n enterState: function(fsm, name, from, to, args) {\n StateMachine.enterThisState(fsm, name, from, to, args);\n StateMachine.enterAnyState( fsm, name, from, to, args);\n },\n\n //===========================================================================\n\n buildEvent: function(name, map) {\n return function() {\n\n var from = this.current;\n var to = map[from] || (map[StateMachine.WILDCARD] != StateMachine.WILDCARD ? map[StateMachine.WILDCARD] : from) || from;\n var args = Array.prototype.slice.call(arguments); // turn arguments into pure array\n\n if (this.transition)\n return this.error(name, from, to, args, StateMachine.Error.PENDING_TRANSITION, \"event \" + name + \" inappropriate because previous transition did not complete\");\n\n if (this.cannot(name))\n return this.error(name, from, to, args, StateMachine.Error.INVALID_TRANSITION, \"event \" + name + \" inappropriate in current state \" + this.current);\n\n if (false === StateMachine.beforeEvent(this, name, from, to, args))\n return StateMachine.Result.CANCELLED;\n\n if (from === to) {\n StateMachine.afterEvent(this, name, from, to, args);\n return StateMachine.Result.NOTRANSITION;\n }\n\n // prepare a transition method for use EITHER lower down, or by caller if they want an async transition (indicated by an ASYNC return value from leaveState)\n var fsm = this;\n this.transition = function() {\n fsm.transition = null; // this method should only ever be called once\n fsm.current = to;\n StateMachine.enterState( fsm, name, from, to, args);\n StateMachine.changeState(fsm, name, from, to, args);\n StateMachine.afterEvent( fsm, name, from, to, args);\n return StateMachine.Result.SUCCEEDED;\n };\n this.transition.cancel = function() { // provide a way for caller to cancel async transition if desired (issue #22)\n fsm.transition = null;\n StateMachine.afterEvent(fsm, name, from, to, args);\n }\n\n var leave = StateMachine.leaveState(this, name, from, to, args);\n if (false === leave) {\n this.transition = null;\n return StateMachine.Result.CANCELLED;\n }\n else if (StateMachine.ASYNC === leave) {\n return StateMachine.Result.PENDING;\n }\n else {\n if (this.transition) // need to check in case user manually called transition() but forgot to return StateMachine.ASYNC\n return this.transition();\n }\n\n };\n }\n\n }; // StateMachine\n\n //===========================================================================\n\n //======\n // NODE\n //======\n if (typeof exports !== 'undefined') {\n if (typeof module !== 'undefined' && module.exports) {\n exports = module.exports = StateMachine;\n }\n exports.StateMachine = StateMachine;\n }\n //============\n // AMD/REQUIRE\n //============\n else if (typeof define === 'function' && define.amd) {\n define(function(require) { return StateMachine; });\n }\n //========\n // BROWSER\n //========\n else if (typeof window !== 'undefined') {\n window.StateMachine = StateMachine;\n }\n //===========\n // WEB WORKER\n //===========\n else if (typeof self !== 'undefined') {\n self.StateMachine = StateMachine;\n }\n\n}());\n","import {AnalyticsStateMachine} from '../../analyticsStateMachines/AnalyticsStateMachine';\nimport {EventDispatcher} from '../../core/EventDispatcher';\nimport QualityChangeService from '../../core/QualityChangeService';\nimport {SourceInfoFallbackService} from '../../core/SourceInfoFallbackService';\nimport {SsaiService} from '../../core/ssai/SsaiService';\nimport {Event, EventMap} from '../../enums/Event';\nimport {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {CustomDataValues} from '../../types/CustomDataValues';\nimport {DownloadSpeedInfo} from '../../types/DownloadSpeedInfo';\nimport {DrmPerformanceInfo} from '../../types/DrmPerformanceInfo';\nimport type {CustomDataValuesEvent} from '../../types/EventData';\nimport {NoExtraProperties} from '../../types/NoExtraProperties';\nimport {SegmentInfo} from '../../types/SegmentInfo';\nimport {defaultStateMachineCallbacks, StateMachineCallbacks} from '../../types/StateMachineCallbacks';\nimport {logger} from '../../utils/Logger';\nimport {getCurrentTimestamp} from '../../utils/Utils';\nimport {WindowEventTracker} from '../../utils/WindowEventTracker';\n\nimport {EventCallbackDispatcher} from './EventCallbackDispatcher';\n\n/**\n * Audio volume below this delta is considered zero.\n */\nconst volumeDelta = 0.01;\n\nexport abstract class InternalAdapter implements EventCallbackDispatcher {\n readonly stateMachineCallbacks: StateMachineCallbacks = {...defaultStateMachineCallbacks};\n readonly qualityChangeService: QualityChangeService = new QualityChangeService();\n readonly ssaiService = new SsaiService();\n\n protected stateMachine!: AnalyticsStateMachine;\n protected opts: AnalyticsStateMachineOptions;\n protected _onLicenseKeyReceived: EventDispatcher<{licenseKey: string}> = new EventDispatcher();\n protected _onLicenseCallFailed: EventDispatcher<any> = new EventDispatcher();\n\n protected sourceInfoFallbackService: SourceInfoFallbackService = new SourceInfoFallbackService();\n protected drmPerformanceInfo: DrmPerformanceInfo | undefined = undefined;\n protected abstract get currentTime(): number;\n\n private _windowEventTracker: WindowEventTracker = new WindowEventTracker();\n\n get windowEventTracker(): WindowEventTracker {\n return this._windowEventTracker;\n }\n\n get onLicenseKeyReceived() {\n return this._onLicenseKeyReceived;\n }\n\n get onLicenseCallFailed() {\n return this._onLicenseCallFailed;\n }\n\n get downloadSpeedInfo(): DownloadSpeedInfo {\n return {\n segmentsDownloadCount: 0,\n segmentsDownloadSize: 0,\n segmentsDownloadTime: 0,\n avgDownloadSpeed: 0,\n minDownloadSpeed: 0,\n maxDownloadSpeed: 0,\n avgTimeToFirstByte: 0,\n };\n }\n\n get segments(): SegmentInfo[] {\n return [];\n }\n\n constructor(opts?: AnalyticsStateMachineOptions) {\n if (!opts) {\n opts = {\n starttime: undefined,\n };\n }\n if (!opts.starttime) {\n opts.starttime = getCurrentTimestamp();\n }\n\n this.opts = opts;\n }\n\n release() {\n this.stateMachine.resetIntervals();\n this.stateMachineCallbacks.release();\n this.resetSourceRelatedState();\n this._windowEventTracker.release();\n }\n\n eventCallback = <StateMachineEvent extends keyof EventMap, StateMachineEventData extends EventMap[StateMachineEvent]>(\n event: StateMachineEvent,\n eventData: NoExtraProperties<EventMap[StateMachineEvent], StateMachineEventData>,\n ) => {\n eventData = eventData || {};\n if (!this.stateMachine) {\n logger.log(\"Bitmovin Analytics: StateMachine isn't ready yet\");\n } else {\n this.stateMachine.callEvent(event, eventData, Date.now());\n }\n };\n\n getCommonPlaybackInfo() {\n let scale = 1;\n if (window.devicePixelRatio > 0) {\n scale = window.devicePixelRatio;\n }\n\n return {\n screenHeight: window.screen.height * scale,\n screenWidth: window.screen.width * scale,\n };\n }\n\n clearValues(): void {\n // noop by default\n }\n\n clearSegments(): void {\n // noop by default\n }\n\n resetSourceRelatedState(): void {\n this.sourceInfoFallbackService.reset();\n this.drmPerformanceInfo = undefined;\n }\n\n setCustomData(values: CustomDataValues): void {\n const previousState = this.stateMachine.currentState;\n const eventData: CustomDataValuesEvent = {customDataValues: values, currentTime: this.currentTime};\n\n if (\n this.stateMachine.currentState &&\n (this.stateMachine.currentState === 'PAUSE' || this.stateMachine.currentState === 'PLAYING')\n ) {\n // If we are in State.PAUSE or State.PLAYING, we want to make \"a cut\" of the current state\n // to trigger sample sending with current custom data values.\n this.eventCallback(Event.CUSTOM_DATA_CHANGE, {currentTime: this.currentTime});\n // Then we have to call this \"previous state\" event to return back\n // to the previous state and to set new custom data values.\n // !! here we relay on the fact that we have `PAUSE` and `PLAYING` events with the same name as the states above !!\n this.eventCallback(Event[previousState], eventData);\n }\n // ... else, for any other states, we don't care, and we will just set new custom data values asap, so they will\n // be sent with the upcoming sample\n else {\n this.stateMachineCallbacks.customdatachange(undefined, undefined, eventData);\n }\n }\n\n protected isAudioMuted(playerIsMuted: boolean, currentVolume: number): boolean {\n return playerIsMuted || currentVolume < volumeDelta;\n }\n}\n","import {AnalyticsEventBase} from '../types/EventData';\n\nexport const DEFAULT_HEARTBEAT_INTERVAL_MS = 59700;\n\nexport interface HeartbeatListener {\n onHeartbeat: (eventObject: AnalyticsEventBase) => void;\n}\n\nexport class HeartbeatService {\n private heartbeatInterval: number | undefined;\n private listener: HeartbeatListener | undefined;\n private readonly getPlayerCurrentTime: () => number;\n\n constructor(getPlayerCurrentTime: () => number) {\n this.getPlayerCurrentTime = getPlayerCurrentTime;\n }\n\n setListener(listener: HeartbeatListener) {\n this.listener = listener;\n }\n\n startHeartbeat() {\n if (this.heartbeatInterval !== undefined) {\n this.clearHeartbeat();\n }\n this.heartbeatInterval = window.setInterval(() => {\n const eventData: AnalyticsEventBase = {\n currentTime: this.getPlayerCurrentTime(),\n };\n this.listener?.onHeartbeat(eventData);\n }, DEFAULT_HEARTBEAT_INTERVAL_MS);\n }\n\n stopHeartbeat() {\n this.clearHeartbeat();\n }\n\n private clearHeartbeat() {\n window.clearTimeout(this.heartbeatInterval);\n this.heartbeatInterval = undefined;\n }\n}\n","export const generateUUID = (): string => {\n return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => {\n const r = (Math.random() * 16) | 0;\n const v = c === 'x' ? r : (r & 0x3) | 0x8;\n return v.toString(16);\n });\n};\n","import {DeferredLicenseLoadingAdapterAPI} from '../adapters/internal/DeferredLicenseLoadingAdapterAPI';\nimport {AnalyticsConfig, CollectorConfig} from '../types/AnalyticsConfig';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {LicensingRequest} from '../types/LicensingRequest';\nimport {LicenseCall} from '../utils/LicenseCall';\nimport {ANALYTICS_BACKEND_BASE_URL} from '../utils/Settings';\n\nimport {Backend} from './Backend';\nimport {DebuggingBackend} from './DebuggingBackend';\nimport {LicenseCheckingBackend} from './LicenseCheckingBackend';\nimport {LongPlaytimeFilteringBackend} from './LongPlaytimeFilteringBackend';\nimport {NoOpBackend} from './NoOpBackend';\nimport {SequenceNumberBackend} from './SequenceNumberBackend';\n\ninterface InternalCollectorConfig extends CollectorConfig {\n wrapBackend: (innerBackend: Backend) => Backend;\n}\n\nexport class BackendFactory {\n createBackend(\n analyticsConfig: AnalyticsConfig,\n licensingRequest: LicensingRequest,\n adapter: DeferredLicenseLoadingAdapterAPI,\n authenticationCallback: AuthenticationCallback,\n ): Backend {\n if (!this.isEnabled(analyticsConfig)) {\n return new NoOpBackend();\n }\n const inner = this.createInnerBackend(analyticsConfig, licensingRequest, adapter, authenticationCallback);\n return this.decorateWithDebuggingBackend(analyticsConfig, inner);\n }\n\n private decorateWithDebuggingBackend(config: AnalyticsConfig, backend: Backend): Backend {\n if (config.debug) {\n return new DebuggingBackend(config, backend);\n }\n return backend;\n }\n\n private decorateWithBackendFromConfigIfAvailable(analyticsConfig: AnalyticsConfig, innerBackend: Backend): Backend {\n if (\n analyticsConfig !== undefined &&\n analyticsConfig.config !== undefined &&\n (analyticsConfig.config as InternalCollectorConfig).wrapBackend !== undefined\n ) {\n return (analyticsConfig.config as InternalCollectorConfig).wrapBackend(innerBackend);\n }\n\n return innerBackend;\n }\n\n private isEnabled(analyticsConfig: AnalyticsConfig): boolean {\n return analyticsConfig.config === undefined || analyticsConfig.config.enabled !== false;\n }\n\n private createInnerBackend(\n analyticsConfig: AnalyticsConfig,\n licensingRequest: LicensingRequest,\n adapter: DeferredLicenseLoadingAdapterAPI,\n authenticationCallback: AuthenticationCallback,\n ): Backend {\n const backendUrl = (analyticsConfig.config && analyticsConfig.config.backendUrl) || ANALYTICS_BACKEND_BASE_URL;\n let innerBackend: Backend = new LicenseCheckingBackend(\n licensingRequest,\n LicenseCall,\n backendUrl,\n adapter,\n authenticationCallback,\n );\n innerBackend = this.decorateWithBackendFromConfigIfAvailable(analyticsConfig, innerBackend);\n\n const sequenceNumberAssigningBackend = new SequenceNumberBackend(innerBackend);\n return new LongPlaytimeFilteringBackend(sequenceNumberAssigningBackend);\n }\n}\n","export class Queue<T> {\n private readonly _items: T[] = [];\n\n get items(): ReadonlyArray<T> {\n return this._items;\n }\n\n get length() {\n return this._items.length;\n }\n\n offer(item: T) {\n this._items.push(item);\n }\n\n poll(): T | undefined {\n return this._items.shift();\n }\n\n clear() {\n this._items.splice(0);\n }\n\n limit(maxElements: number) {\n while (this._items.length > maxElements) {\n this.poll();\n }\n }\n}\n","import {PlayerSize} from '../enums/PlayerSize';\nimport {StreamTypes} from '../enums/StreamTypes';\nimport {isNullish} from '../utils/Utils';\n\nexport interface PlaybackInfo {\n audioBitrate?: number;\n audioCodec?: string;\n audioLanguage?: string;\n castTech?: string;\n droppedFrames: number;\n isCasting?: boolean;\n isLive?: boolean;\n isMuted?: boolean;\n m3u8Url?: string;\n mpdUrl?: string;\n playerTech?: string;\n progUrl?: string;\n screenHeight?: number;\n screenWidth?: number;\n size?: PlayerSize;\n streamFormat?: string;\n subtitleEnabled?: boolean;\n subtitleLanguage?: string;\n videoBitrate?: number;\n videoCodec?: string;\n videoDuration?: number;\n videoPlaybackHeight?: number;\n videoPlaybackWidth?: number;\n videoTitle?: string;\n videoWindowHeight?: number;\n videoWindowWidth?: number;\n}\n\nexport function normalizeVideoDuration(playerVideoDuration: number | null | undefined): number {\n // This covers Live streams and any case in which the duration is not known\n // which should report 0 as videoDuration\n if (isNullish(playerVideoDuration) || Number.isNaN(playerVideoDuration) || playerVideoDuration === Infinity) {\n return 0;\n }\n return playerVideoDuration;\n}\n\nexport function buildPlaybackInfoStreamTypeFields(\n streamType: StreamTypes | undefined,\n streamUrl: string | undefined,\n): Pick<PlaybackInfo, 'm3u8Url' | 'mpdUrl' | 'progUrl' | 'streamFormat'> {\n const DEFAULT_RESULT = {\n // set the stream type as it is (except null, that should be converted to undefined)\n streamFormat: streamType ?? undefined,\n // If the stream url is there, set it as \"progUrl\", even when the stream type is not recognized (unknown / nullish).\n // Why?\n // There was no clear reason why when this utility fn was created, it was just current written code/behavior\n // of our adapters, and for that reason it was copy&pasted here.\n progUrl: streamUrl,\n };\n\n if (isNullish(streamType)) {\n return DEFAULT_RESULT;\n }\n\n if (streamType === StreamTypes.dash) {\n return {streamFormat: streamType, mpdUrl: streamUrl};\n }\n if (streamType === StreamTypes.hls) {\n return {streamFormat: streamType, m3u8Url: streamUrl};\n }\n if (streamType === StreamTypes.prog) {\n return {streamFormat: streamType, progUrl: streamUrl};\n }\n\n return DEFAULT_RESULT;\n}\n","export class ErrorCode {\n static BITMOVIN_PLAYER_LICENSING_ERROR = new ErrorCode(1103, '');\n static SETUP_MISSING_LICENSE_WHITELIST = new ErrorCode(1105, '');\n static QUALITY_CHANGE_THRESHOLD_EXCEEDED = new ErrorCode(10000, 'ANALYTICS_QUALITY_CHANGE_THRESHOLD_EXCEEDED');\n static BUFFERING_TIMEOUT_REACHED = new ErrorCode(10001, 'ANALYTICS_BUFFERING_TIMEOUT_REACHED');\n static VIDEO_STARTUP_TIMEOUT_REACHED = new ErrorCode(10002, 'ANALYTICS_VIDEOSTART_TIMEOUT_REACHED');\n\n private constructor(\n readonly code: number,\n readonly message: string,\n ) {}\n}\n","import {DeferredLicenseLoadingAdapterAPI} from '../adapters/internal/DeferredLicenseLoadingAdapterAPI';\nimport {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {LicenseCallFunc, LicensingRequest, LicensingResponse, LicensingResult} from '../types/LicensingRequest';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\nimport {ANALYTICS_LICENSECALL_TIMEOUT} from '../utils/Settings';\n\nimport {Backend} from './Backend';\nimport {NoOpBackend} from './NoOpBackend';\nimport {QueueBackend} from './QueueBackend';\nimport {RemoteBackend} from './RemoteBackend';\n\n/**\n * The `LicenseCheckingBackend` class is responsible for sending license requests\n * and routing samples to the appropriate backend based on the license status.\n *\n * The class manages a queue of samples during the license check process, ensuring that\n * samples are not lost while the license status is being determined. Once the license\n * is validated, the queued samples are flushed to the appropriate backend.\n *\n * @implements {Backend}\n */\nexport class LicenseCheckingBackend implements Backend {\n promise?: Promise<LicensingResponse>;\n private licenseLazyLoadingTimeoutHandle?: number;\n private backend: Backend;\n private info: LicensingRequest;\n\n constructor(\n info: LicensingRequest,\n private licenseCall: LicenseCallFunc,\n private backendBaseUrl: string,\n private adapter: DeferredLicenseLoadingAdapterAPI,\n private authenticationCallback: AuthenticationCallback,\n ) {\n this.info = {...info};\n this.backend = new QueueBackend();\n this.licenseCall = licenseCall;\n\n if (info.key !== undefined && info.key !== '') {\n this.promise = this.wrapLicenseCheckPromiseWithCallback(this.performLicenseCheck(), this.authenticationCallback);\n } else if (adapter.supportsDeferredLicenseLoading === true) {\n adapter.onLicenseKeyReceived.subscribe(this.licenseKeyReceived);\n adapter.onLicenseCallFailed.subscribe(this.licenseCallFailed);\n this.licenseLazyLoadingTimeoutHandle = window.setTimeout(\n this.licenseLazyLoadingTimeout,\n ANALYTICS_LICENSECALL_TIMEOUT,\n );\n } else {\n authenticationCallback.authenticationCompleted(false, undefined);\n this.backend = new NoOpBackend();\n }\n }\n\n performLicenseCheck(): Promise<LicensingResponse> {\n const {key, domain, version} = this.info;\n if (!key || key === '') {\n const error: LicensingResponse = {\n status: LicensingResult.Denied,\n message: 'No license key provided',\n };\n this.backend = new NoOpBackend();\n return Promise.resolve(error);\n }\n\n return this.licenseCall(key, domain, version, this.backendBaseUrl)\n .then((result) => {\n if (result.status === LicensingResult.Granted) {\n const remoteBackend = new RemoteBackend(true, this.backendBaseUrl, key);\n (this.backend as QueueBackend).flushTo(remoteBackend);\n this.backend = remoteBackend;\n } else {\n throw new Error(result.message);\n }\n return result;\n })\n .catch((err: Error) => {\n if (err.message === 'Ignoring Impression due to DNT Header being set') {\n logger.error('License Check for Bitmovin Analytics failed because of', err);\n } else {\n logger.errorMessageToUser('License Check for Bitmovin Analytics failed because of', err);\n }\n this.backend = new NoOpBackend();\n return {\n status: LicensingResult.Denied,\n message: err.message,\n };\n });\n }\n\n sendRequest(sample: Sample) {\n this.backend.sendRequest(sample);\n }\n sendUnloadRequest(sample: Sample) {\n this.backend.sendUnloadRequest(sample);\n }\n sendRequestSynchronous(sample: Sample) {\n this.backend.sendRequestSynchronous(sample);\n }\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.backend.sendAdRequest(sample);\n }\n\n private licenseKeyReceived = (eventArgs: {licenseKey: string}) => {\n clearTimeout(this.licenseLazyLoadingTimeoutHandle);\n this.unsubscribeFromAdapter();\n this.info.key = eventArgs.licenseKey;\n this.promise = this.wrapLicenseCheckPromiseWithCallback(this.performLicenseCheck(), this.authenticationCallback);\n };\n\n private licenseCallFailed = () => {\n clearTimeout(this.licenseLazyLoadingTimeoutHandle);\n this.unsubscribeFromAdapter();\n this.backend = new NoOpBackend();\n this.authenticationCallback.authenticationCompleted(false, undefined);\n };\n\n private licenseLazyLoadingTimeout = () => {\n this.unsubscribeFromAdapter();\n this.backend = new NoOpBackend();\n this.authenticationCallback.authenticationCompleted(false, undefined);\n };\n\n private unsubscribeFromAdapter() {\n this.adapter.onLicenseKeyReceived.unsubscribe(this.licenseKeyReceived);\n this.adapter.onLicenseCallFailed.unsubscribe(this.licenseCallFailed);\n }\n\n private wrapLicenseCheckPromiseWithCallback(\n promise: Promise<LicensingResponse>,\n authenticationCallback: AuthenticationCallback,\n ): Promise<LicensingResponse> {\n return promise.then((response) => {\n authenticationCallback.authenticationCompleted(response.status === LicensingResult.Granted, response.features);\n return response;\n });\n }\n}\n","import {Event} from './Event';\n\nexport enum VideoStartFailedReason {\n PAGE_CLOSED = 'PAGE_CLOSED',\n PLAYER_ERROR = 'PLAYER_ERROR',\n TIMEOUT = 'TIMEOUT',\n UNKNOWN = 'UNKNOWN',\n}\n\nexport function createVideoStartFailedReason(stateMachineEvent: string | undefined): VideoStartFailedReason {\n switch (stateMachineEvent) {\n case Event.ERROR:\n return VideoStartFailedReason.PLAYER_ERROR;\n case Event.UNLOAD:\n return VideoStartFailedReason.PAGE_CLOSED;\n case Event.VIDEOSTART_TIMEOUT:\n return VideoStartFailedReason.TIMEOUT;\n\n default:\n return VideoStartFailedReason.UNKNOWN;\n }\n}\n","/* eslint-disable perfectionist/sort-enums */\n\nexport enum AD_TYPE {\n NO_AD = 0,\n CSAI = 1,\n SSAI = 2,\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","import {logger} from './Logger';\nimport * as Utils from './Utils';\nimport {isNullish} from './Utils';\n\nexport class ViewportTracker {\n private onIntersectionChanged: () => void;\n private observer?: IntersectionObserver;\n private element: HTMLElement;\n private inViewport?: boolean = undefined;\n private threshold: number;\n private hidden: string | undefined;\n private visibilityChange?: string;\n\n constructor(element: HTMLElement, onIntersectionChanged: () => void, threshold = 1.0) {\n this.threshold = threshold;\n this.onIntersectionChanged = onIntersectionChanged;\n this.element = element;\n\n try {\n const options: IntersectionObserverInit = {\n root: null,\n rootMargin: '0px',\n threshold,\n };\n this.observer = new IntersectionObserver((entries, observer) => this.handleIntersect(entries, observer), options);\n this.observer.observe(element);\n } catch (_error) {\n logger.log(\"Couldn't create instance of IntersectionObserver. timeInViewport will always be reported as 100%.\");\n }\n\n this.hidden = Utils.getHiddenProp();\n if (this.hidden) {\n this.visibilityChange = this.hidden.replace('hidden', '') + 'visibilitychange';\n document.addEventListener(\n this.visibilityChange,\n (this.handleVisibilityChange = this.handleVisibilityChange.bind(this)),\n false,\n );\n }\n }\n\n isHidden() {\n return this.hidden && document[this.hidden];\n }\n\n isInViewport(): boolean {\n return !this.isHidden() && (isNullish(this.inViewport) ? true : this.inViewport);\n }\n\n dispose() {\n if (this.observer) {\n this.observer.unobserve(this.element);\n this.observer.disconnect();\n }\n if (this.visibilityChange) {\n document.removeEventListener(this.visibilityChange, this.handleVisibilityChange, false);\n }\n }\n\n private handleVisibilityChange() {\n this.onIntersectionChanged();\n }\n\n private handleIntersect(entries: IntersectionObserverEntry[], _observer: IntersectionObserver) {\n entries.forEach((i) => {\n if (i.target === this.element) {\n this.inViewport = !(i.intersectionRatio < this.threshold);\n }\n });\n this.onIntersectionChanged();\n }\n}\n","import {SpeedMeasurement} from '../types/SpeedMeasurement';\n\nexport class Measure implements SpeedMeasurement {\n private download: SpeedMeasurement;\n\n get speed(): number {\n return this.download.size / this.download.duration;\n }\n get duration(): number {\n return this.download.duration;\n }\n get size(): number {\n return this.download.size;\n }\n get timeToFirstByte(): number {\n return this.download.timeToFirstByte;\n }\n get timestamp(): Date {\n return this.download.timestamp;\n }\n\n get httpStatus(): number {\n return this.download.httpStatus;\n }\n\n constructor(download: SpeedMeasurement) {\n this.download = download;\n }\n}\n","import type {SsaiAdBreakMetadata} from '../../api/AdapterAPI';\nimport {isNotNullish} from '../../utils/Utils';\n\n/**\n * Utility function to sanitize the adPosition value in the SsaiAdBreakMetadata object passed to Bitmovin8Adapter.\n *\n * Needed, because we have introduced SSAI API in `Bitmovin8Adapter` in v2.39.0, without doing proper validation of\n * the passed adPosition value and customer started to use us with invalid values (having `-` in string in JavaScript).\n * Because we did not want to break the customer's implementation, we decided to sanitize the value to the correct one.\n *\n * @deprecated This function will be removed in v3\n */\nexport const sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition = <T = unknown>(anything: T): T => {\n const maybeSsaiAdBreakMetadata = anything as SsaiAdBreakMetadata;\n\n if (isNotNullish(maybeSsaiAdBreakMetadata?.adPosition)) {\n if ((maybeSsaiAdBreakMetadata.adPosition as string) === 'pre-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'preroll';\n } else if ((maybeSsaiAdBreakMetadata.adPosition as string) === 'mid-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'midroll';\n } else if ((maybeSsaiAdBreakMetadata?.adPosition as string) === 'post-roll') {\n maybeSsaiAdBreakMetadata.adPosition = 'postroll';\n }\n }\n\n return maybeSsaiAdBreakMetadata as T;\n};\n","import type {SsaiAdBreakMetadata, SsaiAdMetadata, SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\nimport {AD_TYPE} from '../../enums/AdType';\nimport {ErrorCode} from '../../enums/ErrorCode';\nimport {customDataValuesKeys} from '../../types/CustomDataValues';\nimport type {AnalyticsEventBase} from '../../types/EventData';\nimport type {Sample} from '../../types/Sample';\nimport {isNotNullish} from '../../utils/Utils';\nimport {generateUUID} from '../../utils/uuidUtils';\n\nimport type {InternalSsaiMetadata, SsaiEngagementInteractionData} from './ssaiEngagementInteractionData';\nimport {\n getCurrentMonotonicTimestampInMs,\n getMonotonicTimestampInMsSince,\n SSAI_RELATED_SAMPLE_MARKER,\n} from './ssaiUtils';\n\nexport type SsaiEventHandler = {\n getPlayerCurrentTime: () => number;\n reportEngagementInteraction: (data: SsaiEngagementInteractionData) => void;\n reportPlaybackInteraction: (timestamp: number, eventData: AnalyticsEventBase) => void;\n};\n\nenum SsaiState {\n AD_BREAK_STARTED,\n ACTIVE,\n IDLE,\n}\n\n// we start with -1, to be able to increment it before sending the first sample\n// this way the current adIndex is the one of the current playing ad\nconst INITIAL_AD_INDEX_VALUE = -1;\n\nexport class SsaiService {\n /** if `undefined` then service is not active and should not do anything, why: initially we activate it only for Bitmovin8 */\n private eventHandler: SsaiEventHandler | undefined = undefined;\n\n /** Index of the current ad in the whole session */\n private adIndex: number = INITIAL_AD_INDEX_VALUE;\n\n private state: SsaiState = SsaiState.IDLE;\n private isFirstSampleOfAd = false;\n /**\n * represents the current playing ad metadata\n * is `undefined` when no ad is playing (after endAdBreak)\n * or omitted by customer\n */\n private currentAdMetadata: InternalSsaiMetadata | undefined;\n\n /**\n * The impression id for the currently playing ad\n * is undefined when no ad is playing\n */\n private currentAdImpressionId: string | undefined;\n\n /** List of quartiles already sent for the current ad */\n private sentAdQuartiles: SsaiAdQuartile[] = [];\n\n /**\n * Flags whether an error was sent during an ad to avoid sending multiple errors for one ad,\n * which would skew e.g. the ad abandonment rate.\n */\n private errorSent: boolean = false;\n\n /**\n * The timestamp marking when the `adStart` method was called.\n * This timestamp is used to calculate the time difference between the `adStart` call\n * and subsequent `adQuartileFinished` or `sendAdEngagementErrorSample` calls.\n */\n private timestampOfAdStart: number | undefined;\n\n activate(eventHandler: SsaiEventHandler) {\n this.eventHandler = eventHandler;\n }\n\n adBreakStart(adBreakMetadata?: SsaiAdBreakMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state != SsaiState.IDLE) {\n return;\n }\n\n this.state = SsaiState.AD_BREAK_STARTED;\n this.currentAdMetadata = {\n ...adBreakMetadata,\n };\n }\n\n adStart(adMetadata?: SsaiAdMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state == SsaiState.IDLE) {\n return;\n }\n\n const timestamp = new Date().getTime();\n const playerCurrentTime = this.eventHandler.getPlayerCurrentTime();\n\n // report playback sample - will be saved in our playback related data lake\n // - with the first adStart call we need to close the current normal playback sample (no ssai ad information yet because SsaiState is not yet set to active)\n // - with all following adStart calls, we will deliver previous ssai ad information (SsaiState is already set to active)\n this.eventHandler.reportPlaybackInteraction(timestamp, {currentTime: playerCurrentTime});\n\n this.state = SsaiState.ACTIVE;\n // to include the adIndex in the next sample which will be the first sample of this started ad\n this.isFirstSampleOfAd = true;\n this.adIndex++;\n\n this.resetAdData();\n\n this.currentAdMetadata = {\n adPosition: this.currentAdMetadata?.adPosition,\n adId: adMetadata?.adId,\n adSystem: adMetadata?.adSystem,\n customData: adMetadata?.customData,\n };\n\n this.currentAdImpressionId = generateUUID();\n this.timestampOfAdStart = getCurrentMonotonicTimestampInMs();\n\n // report engagement sample - will be saved in our ad related data lake\n this.eventHandler.reportEngagementInteraction({\n type: 'started',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n });\n }\n\n adQuartileFinished(adQuartile: SsaiAdQuartile, adQuartileMetadata: SsaiAdQuartileMetadata) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not activated\n return;\n }\n\n if (this.state != SsaiState.ACTIVE) {\n return;\n }\n\n if (this.sentAdQuartiles.includes(adQuartile)) {\n //do nothing if adQuartile was already sent\n return;\n }\n\n this.eventHandler.reportEngagementInteraction({\n type: 'quartile',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId!,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n quartile: adQuartile,\n quartileMetadata: adQuartileMetadata,\n timeSinceAdStartedInMs: getMonotonicTimestampInMsSince(this.timestampOfAdStart),\n });\n this.sentAdQuartiles.push(adQuartile);\n }\n\n adBreakEnd() {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state == SsaiState.IDLE) {\n return;\n }\n\n if (this.state == SsaiState.ACTIVE) {\n const timestamp = new Date().getTime();\n const playerCurrentTime = this.eventHandler.getPlayerCurrentTime();\n this.eventHandler.reportPlaybackInteraction(timestamp, {currentTime: playerCurrentTime});\n }\n\n this.resetAdBreakData();\n }\n\n manipulate(sample: Sample): void {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state != SsaiState.ACTIVE) {\n return;\n }\n\n sample.ad = AD_TYPE.SSAI;\n sample.adId = this.currentAdMetadata?.adId;\n sample.adSystem = this.currentAdMetadata?.adSystem;\n sample.adPosition = this.currentAdMetadata?.adPosition;\n // we only mark the first sample of an ssai ad with the index in the playback/audience data (non ad table)\n // this allows us to count the number of ads\n if (this.isFirstSampleOfAd) {\n sample.adIndex = this.adIndex;\n this.isFirstSampleOfAd = false;\n }\n\n const customData = this.currentAdMetadata?.customData;\n if (isNotNullish(customData)) {\n customDataValuesKeys.forEach((key) => {\n if (customData[key]) {\n sample[key] = customData[key];\n }\n });\n }\n\n sample[SSAI_RELATED_SAMPLE_MARKER] = true; // mark it as ssai sample\n }\n\n sendAdEngagementErrorSample(errorCode: number, errorMessage: string) {\n if (!isActivated(this.eventHandler)) {\n // nothing to do if service is not active\n return;\n }\n\n if (this.state !== SsaiState.ACTIVE) {\n return;\n }\n\n // only send one error sample per ad\n if (this.errorSent) {\n return;\n }\n\n // This error code is related to the Analytics product and is non-fatal.\n // It is not triggered by the Player and does not interrupt or affect playback,\n // so there is no need to report an ad error sample.\n if (errorCode === ErrorCode.QUALITY_CHANGE_THRESHOLD_EXCEEDED.code) {\n return;\n }\n\n this.eventHandler.reportEngagementInteraction({\n type: 'error',\n adIndex: this.adIndex,\n currentAdImpressionId: this.currentAdImpressionId!,\n currentAdMetadata: isNotNullish(this.currentAdMetadata) ? this.currentAdMetadata : {},\n errorCode,\n errorMessage,\n timeSinceAdStartedInMs: getMonotonicTimestampInMsSince(this.timestampOfAdStart),\n });\n this.errorSent = true;\n }\n\n resetSourceRelatedState() {\n this.resetAdBreakData();\n this.adIndex = INITIAL_AD_INDEX_VALUE;\n }\n\n private resetAdBreakData() {\n this.state = SsaiState.IDLE;\n this.isFirstSampleOfAd = false;\n delete this.currentAdMetadata;\n this.resetAdData();\n }\n\n private resetAdData() {\n delete this.currentAdMetadata?.customData;\n delete this.currentAdMetadata?.adId;\n delete this.currentAdMetadata?.adSystem;\n this.errorSent = false;\n this.currentAdImpressionId = undefined;\n this.sentAdQuartiles = [];\n this.timestampOfAdStart = undefined;\n }\n}\n\nfunction isActivated(eventHandler: SsaiEventHandler | undefined): eventHandler is SsaiEventHandler {\n return isNotNullish(eventHandler);\n}\n","import {InternalAdapterAPI} from '../adapters/internal/InternalAdapterAPI';\nimport {AD_TYPE} from '../enums/AdType';\nimport {ErrorCode} from '../enums/ErrorCode';\nimport {PlayerSize} from '../enums/PlayerSize';\nimport {VideoStartFailedReason} from '../enums/VideoStartFailedReason';\nimport {ErrorDetailTrackingSettingsProvider} from '../features/errordetails/ErrorDetailTracking';\nimport {OnErrorDetailEventObject} from '../features/errordetails/OnErrorDetailEventObject';\nimport {FeatureManager} from '../features/FeatureManager';\nimport type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport {AuthenticationCallback} from '../types/AuthenticationCallback';\nimport {CustomDataValues, extractCustomDataFieldsOnly} from '../types/CustomDataValues';\nimport * as EventData from '../types/EventData';\nimport {FeatureConfigContainer} from '../types/FeatureConfigContainer';\nimport {PlaybackInfo} from '../types/PlaybackInfo';\nimport {Sample} from '../types/Sample';\nimport Timespan from '../types/Timespan';\nimport {\n getDeviceInformationFromAnalyticsConfig,\n getDomainFromAnalyticsConfig,\n guardAgainstDuplicatedUserId,\n guardConfigChangeAgainstMissingIsLive,\n guardConfigChangeAgainstMissingTitle,\n mergeAnalyticsConfig,\n} from '../utils/analyticsConfigUtils';\nimport {CodecHelper} from '../utils/CodecHelper';\nimport {logger} from '../utils/Logger';\nimport {isBlank, isValidString} from '../utils/stringUtils';\nimport * as Utils from '../utils/Utils';\nimport {isNotNullish, isNullish} from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\nimport {VERSION} from '../utils/Version';\nimport {getWebOSTVModelName, hasWindowWebOSApi} from '../utils/WebOSUtils';\n\nimport {AdAnalytics} from './AdAnalytics';\nimport {Backend} from './Backend';\nimport {BackendFactory} from './BackendFactory';\nimport {EventDispatcher, Subscribable} from './EventDispatcher';\nimport {IdenticalErrorReportingLimiter} from './IdenticalErrorReportingLimiter';\nimport {NoOpBackend} from './NoOpBackend';\nimport {SessionPersistenceHandler} from './SessionPersistenceHandler';\nimport {\n isSsaiEngagementErrorData,\n isSsaiEngagementQuartileData,\n isSsaiEngagementStartedData,\n SsaiEngagementInteractionData,\n} from './ssai/ssaiEngagementInteractionData';\nimport {\n createErrorAdSample,\n createQuartileAdSample,\n createStartedAdSample,\n SSAI_RELATED_SAMPLE_MARKER,\n} from './ssai/ssaiUtils';\n\nexport class Analytics {\n get version(): string {\n return VERSION;\n }\n\n static version: string = VERSION;\n\n private readonly adAnalytics: AdAnalytics | undefined;\n\n pageLoadTime = 0;\n playerStartupTime = 0;\n videoStartupTime = 0;\n autoplay: boolean | undefined = undefined;\n sample: Sample;\n backend!: Backend;\n errorDetailTrackingSettingsProvider: ErrorDetailTrackingSettingsProvider;\n\n private config: AnalyticsConfig;\n private droppedSampleFrames = 0;\n private startupTime = 0;\n\n private authenticationCallback: AuthenticationCallback = {\n authenticationCompleted: (success: boolean, featureConfigs?: FeatureConfigContainer) => {\n this.featureManager.configureFeatures(success, featureConfigs);\n },\n };\n\n // used only in tests to inject mocks\n constructor(\n initialAnalyticsConfig: AnalyticsConfig,\n private readonly adapter: InternalAdapterAPI,\n private readonly backendFactory: BackendFactory,\n private readonly sessionHandler: SessionPersistenceHandler,\n private readonly featureManager: FeatureManager<FeatureConfigContainer>,\n private readonly onErrorDetailEventDispatcher: EventDispatcher<OnErrorDetailEventObject>,\n private readonly identicalErrorReportingLimiter: IdenticalErrorReportingLimiter,\n ) {\n this.config = initialAnalyticsConfig;\n this.sessionHandler = new SessionPersistenceHandler(this.config);\n\n // eslint-disable-next-line @typescript-eslint/no-this-alias\n const that = this;\n this.errorDetailTrackingSettingsProvider = {\n get domain() {\n return getDomainFromAnalyticsConfig(that.config);\n },\n get licenseKey() {\n return that.config.key ?? '';\n },\n get impressionId() {\n return that.getCurrentImpressionId() ?? '';\n },\n get collectorConfig() {\n return that.config.config;\n },\n };\n\n const licenseKeyReceivedUnsubscriber = this.adapter.onLicenseKeyReceived.subscribe(\n (eventArgs: {licenseKey: string}) => {\n if (!this.config.key) {\n this.config.key = eventArgs.licenseKey;\n }\n licenseKeyReceivedUnsubscriber();\n },\n );\n\n this.sample = this.setupSample();\n this.init();\n this.setupStateMachineCallbacks();\n const features = this.adapter.initialize(this);\n this.featureManager.registerFeatures(features);\n\n if (this.adapter.adModule) {\n this.adAnalytics = new AdAnalytics(this, this.adapter.adModule);\n }\n }\n\n get errorDetailSubscribable(): Subscribable<OnErrorDetailEventObject> {\n return this.onErrorDetailEventDispatcher;\n }\n\n getPlayerInformationFromAdapter() {\n const player = this.config.player || this.adapter.getPlayerName();\n return {\n player,\n version: player + '-' + this.adapter.getPlayerVersion(),\n playerTech: this.adapter.getPlayerTech(),\n };\n }\n\n init() {\n if (\n this.adapter.supportsDeferredLicenseLoading !== true &&\n (!isValidString(this.config.key) || isBlank(this.config.key))\n ) {\n logger.errorMessageToUser('Invalid analytics license key provided');\n return;\n }\n\n logger.initialize(this.config.debug);\n\n this.featureManager.resetFeatures();\n this.backend = this.createBackend(this.config);\n this.videoStartupTime = 0;\n this.identicalErrorReportingLimiter.reset();\n\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n\n this.generateNewImpressionId();\n this.setUserId();\n\n if (this.adapter.videoCompletionTracker) {\n this.adapter.videoCompletionTracker.reset();\n }\n\n this.adapter.qualityChangeService.resetValues();\n this.adapter.ssaiService.resetSourceRelatedState();\n }\n\n release() {\n this.backend = new NoOpBackend();\n this.adAnalytics?.release();\n this.adapter.qualityChangeService.stopResetInterval();\n this.identicalErrorReportingLimiter.reset();\n }\n\n setConfigParameters() {\n this.sample.key = this.config.key;\n this.sample.playerKey = this.config.playerKey;\n if (this.config.player) {\n this.sample.player = this.config.player;\n }\n this.sample.domain = getDomainFromAnalyticsConfig(this.config);\n\n this.sample.deviceInformation = getDeviceInformationFromAnalyticsConfig(this.config);\n\n this.sample.cdnProvider = this.config.cdnProvider;\n this.sample.videoId = this.config.videoId;\n this.sample.videoTitle = this.config.title;\n this.sample.customUserId = this.config.userId ?? this.config.customUserId;\n\n Utils.transferCustomDataFields(this.config, this.sample);\n\n this.sample.experimentName = this.config.experimentName;\n }\n\n generateNewImpressionId() {\n this.sample.impressionId = generateUUID();\n }\n\n setUserId() {\n this.sample.userId = this.sessionHandler.userId;\n }\n\n setAutoDetectedDeviceInformation(): void {\n // do not overwrite existing model value (set through config)\n if (isNotNullish(this.sample.deviceInformation?.model)) {\n return;\n }\n\n if (!hasWindowWebOSApi()) return;\n\n const modelName = getWebOSTVModelName();\n if (isNullish(modelName)) return;\n\n this.sample.deviceInformation = this.sample.deviceInformation ?? {};\n this.sample.deviceInformation.model = modelName;\n }\n\n private setupStateMachineCallbacks() {\n // All of these are called in the onLeaveState Method.\n // So it's the last sample\n this.adapter.stateMachineCallbacks.setup = (duration: number, state: string) => {\n logger.log(\n 'Setup bitmovin analytics ' + this.sample.analyticsVersion + ' with impressionId: ' + this.sample.impressionId,\n );\n\n this.setDuration(duration);\n this.setState(state);\n this.playerStartupTime = this.sample.playerStartupTime = duration;\n\n if (window.performance && window.performance.timing) {\n const loadTime = Utils.getCurrentTimestamp() - window.performance.timing.navigationStart;\n this.pageLoadTime = this.sample.pageLoadTime = loadTime;\n }\n\n this.startupTime = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n\n this.sample.pageLoadTime = 0;\n };\n\n this.adapter.stateMachineCallbacks.startup = (duration: number, state: string) => {\n this.sample.supportedVideoCodecs = CodecHelper.supportedVideoFormats;\n this.setState(state);\n\n // videoStartupTime has to be > 0 on startup sample\n // it is used to mark a successfull impression and billing depends on it\n const sanitizedStartupDuration = Math.max(duration, 1);\n\n const startupTimeSum = (this.startupTime || 0) + sanitizedStartupDuration;\n this.sample.startupTime = startupTimeSum;\n this.startupTime = startupTimeSum;\n\n this.setDuration(sanitizedStartupDuration);\n this.videoStartupTime = sanitizedStartupDuration;\n this.sample.videoStartupTime = sanitizedStartupDuration;\n\n this.autoplay = this.sample.autoplay = this.adapter.getAutoPlay();\n this.adapter.qualityChangeService.setStartupHasFinished();\n\n const drmPerformance = this.adapter.getDrmPerformanceInfo();\n if (isNotNullish(drmPerformance)) {\n this.sample.drmType = drmPerformance.drmType;\n this.sample.drmLoadTime = drmPerformance.drmLoadTime;\n }\n\n this.sendAnalyticsRequestAndClearValues();\n this.sample.autoplay = undefined;\n };\n\n this.adapter.stateMachineCallbacks.playing = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.played = duration;\n this.setCompletionValues();\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.unload = (duration: number, state: string) => {\n let videoStartForClosedState = this.sample.videoTimeStart;\n if (state === 'playing') {\n this.setDuration(duration);\n this.setState(state);\n this.sample.played = duration;\n this.setCompletionValues();\n this.sendUnloadRequest();\n if (Utils.isNumber(this.sample.videoTimeEnd)) {\n videoStartForClosedState = this.sample.videoTimeEnd;\n }\n }\n\n if (this.videoStartupTime > 0) {\n this.setVideoTimeStart(videoStartForClosedState);\n this.setVideoTimeEnd(videoStartForClosedState);\n this.clearValues();\n this.setState('closed');\n this.sendUnloadRequest();\n }\n };\n\n this.adapter.stateMachineCallbacks.heartbeat = (duration, state, heartbeatPayload) => {\n this.setState(state);\n this.setDuration(duration);\n\n this.sample = {\n ...this.sample,\n ...heartbeatPayload,\n };\n\n if (state === 'playing') {\n this.setCompletionValues();\n }\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.qualitychange = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.qualitychange_pause = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.qualitychange_rebuffering = (duration: number, state: string) => {\n this.sendQualityChange(state, duration);\n };\n\n this.adapter.stateMachineCallbacks.videoChange = (event: any) => {\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n this.setPlaybackVideoPropertiesFromEvent(event);\n };\n\n this.adapter.stateMachineCallbacks.audioChange = (event: any) => {\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n this.setPlaybackAudioPropertiesFromEvent(event);\n };\n\n this.adapter.stateMachineCallbacks.audiotrack_changing = () => {\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.pause = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n\n this.sample.paused = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n /** @deprecated this function was created only to unify the sample sending for seeking, until deprecated callbacks are removed. */\n const sendSeekingSample = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.seeked = duration;\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.seeking = (duration: number) => sendSeekingSample(duration, 'seeking');\n this.adapter.stateMachineCallbacks.paused_seeking = sendSeekingSample;\n this.adapter.stateMachineCallbacks.end_play_seeking = sendSeekingSample;\n\n this.adapter.stateMachineCallbacks.rebuffering = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n\n this.sample.buffered = duration;\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.videoStartFailed = (duration, reason) => {\n this.setState('startup');\n this.sample.videoStartFailed = true;\n this.sample.videoStartFailedReason = reason;\n this.sample.duration = duration;\n\n if (reason === VideoStartFailedReason.PLAYER_ERROR) {\n // on player error we should not send a video startup sample\n return;\n }\n\n if (reason === VideoStartFailedReason.TIMEOUT) {\n this.sample.errorCode = ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED.code;\n this.sample.errorMessage = ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED.message;\n\n this.onErrorDetailEventDispatcher.dispatch({\n ...ErrorCode.VIDEO_STARTUP_TIMEOUT_REACHED,\n });\n }\n\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.error = (event: Readonly<EventData.ErrorEvent>) => {\n if (event.code && !this.identicalErrorReportingLimiter.shouldReportError(event.code)) {\n logger.log(\n `Bitmovin Analytics: Processing of the error with code ${event.code} was ignored because the error limit was exceeded.`,\n );\n return;\n }\n\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent(event);\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent(event);\n\n this.setState('error');\n this.sample.errorCode = event.code;\n this.sample.errorMessage = event.message;\n this.sample.errorData = JSON.stringify(event.legacyData);\n this.sample.errorSegments = this.adapter.segments.map((s) => s.name);\n\n if (this.adapter.onError) {\n this.adapter.onError();\n }\n\n this.onErrorDetailEventDispatcher.dispatch({\n code: event.code,\n message: event.message,\n errorData: event.data,\n });\n\n this.sendAnalyticsRequestAndClearValues();\n\n delete this.sample.errorCode;\n delete this.sample.errorMessage;\n delete this.sample.errorData;\n };\n\n this.adapter.stateMachineCallbacks.ad = (duration: number, state: string) => {\n this.setDuration(duration);\n this.setState(state);\n this.sample.ad = AD_TYPE.CSAI;\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.mute = () => {\n this.sample.isMuted = true;\n };\n\n this.adapter.stateMachineCallbacks.unMute = () => {\n this.sample.isMuted = false;\n };\n\n this.adapter.stateMachineCallbacks.subtitle_changing = () => {\n this.sendAnalyticsRequestAndClearValues();\n };\n\n this.adapter.stateMachineCallbacks.setVideoTimeEndFromEvent = (analyticsEventBase) => {\n // if we don't have the current playback time, skip and do nothing\n if (!Utils.isNumber(analyticsEventBase?.currentTime)) {\n return;\n }\n\n this.setVideoTimeEnd(Utils.calculateTime(analyticsEventBase.currentTime));\n };\n\n this.adapter.stateMachineCallbacks.setVideoTimeStartFromEvent = (analyticsEventBase) => {\n // if we don't have the current playback time, skip and do nothing\n if (!Utils.isNumber(analyticsEventBase?.currentTime)) {\n return;\n }\n\n this.setVideoTimeStart(Utils.calculateTime(analyticsEventBase.currentTime));\n };\n\n this.adapter.stateMachineCallbacks.manualSourceChange = (event: {config: AnalyticsConfig}) => {\n this.adapter.resetSourceRelatedState();\n this.sample = this.setupSample();\n this.startupTime = 0;\n this.config = Object.keys(event.config).length > 0 ? event.config : this.config;\n this.init();\n };\n\n this.adapter.stateMachineCallbacks.initialSourceChange = (event: {config: AnalyticsConfig}) => {\n this.config = event.config;\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n // The video has ended and we set up for a new impression\n this.adapter.stateMachineCallbacks.end = () => {\n this.sample = this.setupSample();\n this.startupTime = 0;\n this.init();\n };\n\n this.adapter.stateMachineCallbacks.release = () => {\n this.release();\n };\n\n this.adapter.stateMachineCallbacks.customdatachange = (_duration, _state, eventData) => {\n if (isNotNullish(eventData?.customDataValues)) {\n this.changeCustomData(eventData.customDataValues);\n }\n };\n }\n\n sourceChange = (config: AnalyticsConfig | null | undefined) => {\n logger.log('Processing Source Change for Analytics', config);\n if (isNullish(config)) {\n this.adapter.sourceChange(this.config);\n return;\n }\n\n guardConfigChangeAgainstMissingTitle(this.config, config);\n guardConfigChangeAgainstMissingIsLive(this.config, config);\n guardAgainstDuplicatedUserId(config);\n\n const newConfig = mergeAnalyticsConfig(this.config, config);\n this.adapter.sourceChange(newConfig);\n };\n\n setCustomDataOnce = (values: CustomDataValues) => {\n const oldConfig = {...this.config};\n this.setState('customdatachange');\n this.sendAnalyticsRequestAndClearValues(values);\n // this method doesn't call changeCustomData() second time because in that method we have check for null values\n // to prevent overriding existing customData values with null if some field in object doesn't have value\n // because of that if some customData field had previous value null and it got changed to something else\n // it will not be possible to return it back to null using that method\n this.config = {...oldConfig};\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n setCustomData = (values: CustomDataValues) => {\n this.adapter.setCustomData(values);\n };\n\n getCurrentImpressionId = (): string | undefined => {\n return this.sample.impressionId;\n };\n\n getUserId = (): string => {\n return this.sessionHandler.userId;\n };\n\n setDuration(duration: number) {\n this.sample.duration = duration;\n }\n\n setState(state: string) {\n this.sample.state = state;\n }\n\n setPlaybackVideoPropertiesFromEvent(event: any) {\n if (Utils.isNumber(event.width)) {\n this.sample.videoPlaybackWidth = event.width;\n }\n if (Utils.isNumber(event.height)) {\n this.sample.videoPlaybackHeight = event.height;\n }\n if (Utils.isNumber(event.bitrate)) {\n this.sample.videoBitrate = event.bitrate;\n }\n if (isValidString(event.codec)) {\n this.sample.videoCodec = event.codec;\n }\n }\n\n setPlaybackAudioPropertiesFromEvent(event: any) {\n if (Utils.isNumber(event.bitrate)) {\n this.sample.audioBitrate = event.bitrate;\n }\n if (isValidString(event.codec)) {\n this.sample.audioCodec = event.codec;\n }\n }\n\n setPlaybackInfoFromAdapter() {\n const info = this.adapter.getCurrentPlaybackInfo();\n if (!info) {\n return;\n }\n\n // if set, we always apply `config.isLive` in favor of `info.isLive`\n this.sample.isLive = isNotNullish(this.config.isLive) ? this.config.isLive : info.isLive;\n // if `isLive` is still not defined, we set it to default `false` value\n if (isNullish(this.sample.isLive)) {\n this.sample.isLive = false;\n }\n\n if (isValidString(info.size)) {\n this.sample.size = info.size;\n }\n if (isValidString(info.playerTech)) {\n this.sample.playerTech = info.playerTech;\n }\n if (Utils.isNumber(info.videoDuration)) {\n this.sample.videoDuration = Utils.calculateTime(info.videoDuration || 0);\n }\n if (isValidString(info.streamFormat)) {\n this.sample.streamFormat = info.streamFormat;\n }\n if (isValidString(info.mpdUrl)) {\n this.sample.mpdUrl = info.mpdUrl;\n }\n if (isValidString(info.m3u8Url)) {\n this.sample.m3u8Url = info.m3u8Url;\n }\n if (isValidString(info.progUrl)) {\n this.sample.progUrl = info.progUrl;\n }\n if (Utils.isNumber(info.videoWindowWidth)) {\n this.sample.videoWindowWidth = info.videoWindowWidth;\n }\n if (Utils.isNumber(info.videoWindowHeight)) {\n this.sample.videoWindowHeight = info.videoWindowHeight;\n }\n if (Utils.isNumber(info.screenHeight)) {\n this.sample.screenHeight = info.screenHeight;\n }\n if (Utils.isNumber(info.screenWidth)) {\n this.sample.screenWidth = info.screenWidth;\n }\n if (Utils.isBoolean(info.isMuted)) {\n this.sample.isMuted = info.isMuted;\n }\n if (Utils.isBoolean(info.isCasting)) {\n this.sample.isCasting = info.isCasting;\n }\n if (isValidString(info.castTech)) {\n this.sample.castTech = info.castTech;\n }\n if (isValidString(info.videoTitle) && !this.config.title) {\n this.sample.videoTitle = info.videoTitle;\n }\n if (isValidString(info.audioCodec)) {\n this.sample.audioCodec = info.audioCodec;\n }\n if (isValidString(info.videoCodec)) {\n this.sample.videoCodec = info.videoCodec;\n }\n if (isValidString(info.audioLanguage)) {\n this.sample.audioLanguage = info.audioLanguage;\n }\n if (Utils.isBoolean(info.subtitleEnabled)) {\n this.sample.subtitleEnabled = info.subtitleEnabled;\n }\n if (isValidString(info.subtitleLanguage)) {\n this.sample.subtitleLanguage = info.subtitleLanguage;\n } else {\n this.sample.subtitleLanguage = undefined;\n }\n if (Utils.isNumber(info.droppedFrames)) {\n this.sample.droppedFrames = Math.max(info.droppedFrames - this.droppedSampleFrames, 0);\n this.droppedSampleFrames = info.droppedFrames;\n }\n }\n\n setupSample(): Sample {\n this.droppedSampleFrames = 0;\n\n return {\n platform: 'web',\n playerStartupTime: 0,\n pageLoadType: Utils.getPageLoadType(),\n path: Utils.sanitizePath(window.location.pathname),\n language: navigator.language || (navigator as any).userLanguage,\n userAgent: navigator.userAgent,\n screenWidth: screen.width,\n screenHeight: screen.height,\n isLive: this.config.isLive ?? false,\n videoDuration: 0,\n size: PlayerSize.Window,\n time: 0,\n videoWindowWidth: 0,\n videoWindowHeight: 0,\n droppedFrames: 0,\n played: 0,\n buffered: 0,\n paused: 0,\n ad: 0,\n seeked: 0,\n videoPlaybackWidth: 0,\n videoPlaybackHeight: 0,\n videoBitrate: 0,\n audioBitrate: 0,\n videoTimeStart: 0,\n videoTimeEnd: 0,\n videoStartupTime: 0,\n duration: 0,\n startupTime: 0,\n analyticsVersion: VERSION,\n pageLoadTime: 0,\n completedTotal: 0,\n ...this.getPlayerInformationFromAdapter(),\n };\n }\n\n sendAnalyticsRequest(customDataOnceValues?: CustomDataValues) {\n this.setPlaybackInfoFromAdapter();\n this.sample.time = Utils.getCurrentTimestamp();\n this.sample.downloadSpeedInfo = this.adapter.downloadSpeedInfo;\n\n this.adapter.ssaiService.manipulate(this.sample);\n\n // if we have received custom data from the setCustomDataOnce API call, we need to set\n // them as \"the last one\" (we need to override normal customData and SSAI custom data)\n if (customDataOnceValues != null) {\n this.changeCustomData(customDataOnceValues);\n }\n\n // Initial quality info should be available for the first sample after setup, so if there is no quality info yet, we try to set it *before* sending a sample.\n // In the general case, a qualitychange event first triggers a sample of the state we were in before the qualitychange sample itself is sent.\n // So to only report quality updates on the qualitychange sample and not the ones before it, we need to update the quality info *after* sending a sample,\n // making it available for future samples (e.g. qualitychange sample).\n // We only check videoBitrate and not audioBitrate since the latter is often reported as null/0 anyways.\n if (isNullish(this.sample.videoBitrate) || this.sample.videoBitrate <= 0) {\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n const copySample = {...this.sample};\n this.backend.sendRequest(copySample);\n } else {\n const copySample = {...this.sample};\n this.backend.sendRequest(copySample);\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n }\n }\n\n sendAnalyticsRequestAndClearValues(customDataOnceValues?: CustomDataValues) {\n this.sendAnalyticsRequest(customDataOnceValues);\n this.clearValues();\n }\n\n sendSsaiEngagementAdSample(data: SsaiEngagementInteractionData) {\n if (this.config.config?.ssaiEngagementTrackingEnabled !== true) {\n // if not enabled in config, do not send SSAI engagement AdSample\n return;\n }\n\n if (isSsaiEngagementStartedData(data)) {\n const ssaiAdSample = createStartedAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiAdSample);\n return;\n }\n\n if (isSsaiEngagementQuartileData(data)) {\n const ssaiAdSample = createQuartileAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiAdSample);\n return;\n }\n\n if (isSsaiEngagementErrorData(data)) {\n const ssaiErrorAdSample = createErrorAdSample(this.sample, data);\n\n this.backend.sendAdRequest(ssaiErrorAdSample);\n return;\n }\n }\n\n sendUnloadRequest() {\n this.backend.sendUnloadRequest(this.sample);\n }\n\n clearValues() {\n this.sample.ad = 0;\n this.sample.paused = 0;\n this.sample.played = 0;\n this.sample.seeked = 0;\n this.sample.buffered = 0;\n\n this.sample.playerStartupTime = 0;\n this.sample.videoStartupTime = 0;\n this.sample.startupTime = 0;\n this.sample.castTech = undefined;\n\n this.sample.duration = 0;\n this.sample.droppedFrames = 0;\n\n this.sample.drmLoadTime = undefined;\n\n this.sample.videoStartFailed = undefined;\n this.sample.videoStartFailedReason = undefined;\n\n this.sample.completed = undefined;\n\n this.sample.adId = undefined;\n this.sample.adSystem = undefined;\n this.sample.adPosition = undefined;\n this.sample.adIndex = undefined;\n\n this.sample[SSAI_RELATED_SAMPLE_MARKER] = undefined;\n\n this.adapter.clearValues();\n }\n\n /**\n * This method sanitizes the input and updates the analytics config.\n * @param values Object containing the customData and other fields\n */\n private changeCustomData = (values: CustomDataValues) => {\n this.config = {\n ...this.config,\n ...extractCustomDataFieldsOnly(values),\n };\n this.setConfigParameters();\n this.setAutoDetectedDeviceInformation();\n };\n\n private createBackend(config: AnalyticsConfig): Backend {\n const domain = getDomainFromAnalyticsConfig(config);\n return this.backendFactory.createBackend(\n config,\n {key: config.key, domain, version: VERSION},\n this.adapter,\n this.authenticationCallback,\n );\n }\n\n private setCompletionValues() {\n if (this.adapter.videoCompletionTracker) {\n const completed = this.adapter.videoCompletionTracker.addWatched({\n start: this.sample.videoTimeStart,\n end: this.sample.videoTimeEnd,\n } as Timespan);\n const completedTotal = this.adapter.videoCompletionTracker.getCompletionPercentage();\n\n if (!Number.isNaN(completed) && !Number.isNaN(completedTotal)) {\n this.sample.completed = completed;\n this.sample.completedTotal = completedTotal;\n }\n }\n }\n\n private setVideoTimeStart(value: number | undefined) {\n this.sample.videoTimeStart = value;\n }\n\n private setVideoTimeEnd(value: number | undefined) {\n this.sample.videoTimeEnd = value;\n }\n\n private sendQualityChange(state: string, duration: number): void {\n this.adapter.qualityChangeService.startResetInterval();\n\n this.adapter.qualityChangeService.increaseCounter();\n if (!this.adapter.qualityChangeService.isQualityChangeEventEnabled()) {\n this.setDuration(duration);\n this.adapter.stateMachineCallbacks.error({\n ...ErrorCode.QUALITY_CHANGE_THRESHOLD_EXCEEDED,\n legacyData: undefined,\n currentTime: undefined,\n data: {\n /*TODO additionalData: 'Add description for this error'*/\n },\n });\n } else {\n setQualityInfoOnSample(this.sample, this.adapter.getCurrentPlaybackInfo());\n this.setDuration(duration);\n this.setState(state);\n this.sendAnalyticsRequestAndClearValues();\n }\n }\n\n static create(config: AnalyticsConfig, adapter: InternalAdapterAPI): Analytics {\n const backendFactory: BackendFactory = new BackendFactory();\n const sessionHandler: SessionPersistenceHandler = new SessionPersistenceHandler(config);\n const featureManager = new FeatureManager<FeatureConfigContainer>();\n const onErrorDetailEventDispatcher = new EventDispatcher<OnErrorDetailEventObject>();\n const identicalErrorReportingLimiter = new IdenticalErrorReportingLimiter();\n return new Analytics(\n config,\n adapter,\n backendFactory,\n sessionHandler,\n featureManager,\n onErrorDetailEventDispatcher,\n identicalErrorReportingLimiter,\n );\n }\n}\n\n// We separate the quality info from `setPlaybackInfoFromAdapter` to be able to explicitly set/update the quality info only when it changes.\nexport function setQualityInfoOnSample(sample: Sample, playbackInfo: PlaybackInfo) {\n if (Utils.isNumber(playbackInfo.videoPlaybackHeight)) {\n sample.videoPlaybackHeight = playbackInfo.videoPlaybackHeight;\n }\n if (Utils.isNumber(playbackInfo.videoPlaybackWidth)) {\n sample.videoPlaybackWidth = playbackInfo.videoPlaybackWidth;\n }\n if (Utils.isNumber(playbackInfo.videoBitrate)) {\n sample.videoBitrate = playbackInfo.videoBitrate;\n }\n if (Utils.isNumber(playbackInfo.audioBitrate)) {\n sample.audioBitrate = playbackInfo.audioBitrate;\n }\n}\n","export enum CdnProvider {\n AKAMAI = 'akamai',\n BITGRAVITY = 'bitgravity',\n CHINACACHE = 'chinacache',\n CLOUDFLARE = 'cloudflare',\n CLOUDFRONT = 'cloudfront',\n FASTLY = 'fastly',\n MAXCDN = 'maxcdn',\n}\n","/*!\n * This file was created to only avoid \"values imports\" (constants/enums/classes/etc.) from the `bitmovin-player@8.220.0`\n * to avoid including the whole package in our distribution code.\n *\n * We should still use \"type imports\" (`import type {}`) from the library!\n *\n * Unit test should cover \"copies of the library values\" to be sure they are up to date with the library!\n */\n\n/* eslint-disable perfectionist/sort-enums */\n\n/**\n * Copy of `HttpRequestType` enum from Bitmovin Player\n *\n * @see https://github.com/bitmovin-engineering/bitdash/blob/v8.220.0/src/core/NetworkAPI.ts#L11\n */\nexport enum HttpRequestType {\n MANIFEST_DASH = 'manifest/dash',\n MANIFEST_HLS_MASTER = 'manifest/hls/master',\n MANIFEST_HLS_VARIANT = 'manifest/hls/variant',\n MANIFEST_SMOOTH = 'manifest/smooth',\n MANIFEST_ADS = 'manifest/ads',\n\n MEDIA_AUDIO = 'media/audio',\n MEDIA_VIDEO = 'media/video',\n MEDIA_SUBTITLES = 'media/subtitles',\n MEDIA_THUMBNAILS = 'media/thumbnails',\n MEDIA_SEGMENTINDEX = 'media/segmentindex',\n\n DRM_LICENSE_WIDEVINE = 'drm/license/widevine',\n DRM_LICENSE_PLAYREADY = 'drm/license/playready',\n DRM_LICENSE_FAIRPLAY = 'drm/license/fairplay',\n DRM_LICENSE_PRIMETIME = 'drm/license/primetime',\n DRM_LICENSE_CLEARKEY = 'drm/license/clearkey',\n DRM_LICENSE_TVKEY = 'drm/license/tvkey',\n\n DRM_CERTIFICATE_FAIRPLAY = 'drm/certificate/fairplay',\n\n KEY_HLS_AES = 'key/hls/aes',\n\n TIME_SYNC = 'time/sync',\n\n WEBRTC_SDP_REQUEST = 'webrtc/sdp/request',\n WEBRTC_SDP_ANSWER = 'webrtc/sdp/answer',\n WEBRTC_SDP_OFFER = 'webrtc/sdp/offer',\n\n UNKNOWN = 'unknown',\n\n INTERNAL = 'internal',\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","import type {Ad, LinearAd, VastAdData} from 'bitmovin-player';\n\nimport * as Utils from '../utils/Utils';\n\nexport class AdSample {\n private static parseSkipAfter(skipAfter?: number) {\n if (skipAfter === undefined) {\n return undefined;\n }\n if (skipAfter === -1) {\n return skipAfter;\n }\n return Utils.calculateTime(skipAfter);\n }\n\n wrapperAdsCount?: number;\n adSkipAfter?: number;\n adSkippable?: boolean;\n adClickthroughUrl?: string;\n adDescription?: string;\n adDuration?: number;\n adId?: string;\n adImpressionId?: string;\n adPlaybackHeight?: number;\n adPlaybackWidth?: number;\n adStartupTime?: number;\n adSystem?: string;\n adTitle?: string;\n advertiserName?: string;\n apiFramework?: string;\n audioBitrate?: number;\n clicked = 0;\n clickPosition?: number;\n closed = 0;\n closePosition?: number;\n completed = 0;\n creativeAdId?: string;\n creativeId?: string;\n dealId?: string;\n isLinear?: boolean;\n mediaPath?: string;\n mediaServer?: string;\n mediaUrl?: string;\n midpoint = 0;\n minSuggestedDuration?: number;\n percentageInViewport?: number;\n quartile1 = 0;\n quartile3 = 0;\n skipped = 0;\n skipPosition?: number;\n started = 0;\n streamFormat?: string;\n surveyUrl?: string;\n time?: number;\n timeHovered?: number;\n timeInViewport?: number;\n timePlayed?: number;\n timeUntilHover?: number;\n universalAdIdRegistry?: string;\n universalAdIdValue?: string;\n videoBitrate?: number;\n adPodPosition?: number;\n exitPosition?: number;\n playPercentage?: number;\n skipPercentage?: number;\n clickPercentage?: number;\n closePercentage?: number;\n errorPosition?: number;\n errorPercentage?: number;\n timeToContent?: number;\n timeFromContent?: number;\n\n constructor(ad?: Ad) {\n if (ad) {\n this.adClickthroughUrl = ad.clickThroughUrl;\n this.adId = ad.id;\n this.mediaUrl = ad.mediaFileUrl;\n const mediaUrlDetails = Utils.getHostnameAndPathFromUrl(this.mediaUrl || '');\n this.mediaPath = mediaUrlDetails.path;\n this.mediaServer = mediaUrlDetails.hostname;\n this.isLinear = ad.isLinear;\n this.adPlaybackHeight = ad.height;\n this.adPlaybackWidth = ad.width;\n\n if (ad.data) {\n this.videoBitrate = ad.data.bitrate === undefined ? undefined : ad.data.bitrate * 1000;\n this.streamFormat = ad.data.mimeType;\n // data.minBitrate\n // data.maxBitrate\n }\n\n const data = ad.data as VastAdData;\n if (data) {\n if (data.adSystem) {\n this.adSystem = data.adSystem.name;\n // this.adSystemVersion = data.adSystem.version;\n }\n if (data.advertiser) {\n this.advertiserName = data.advertiser.name;\n // this.advertiserId = data.advertiser.id;\n }\n // data.codec\n // data.delivery\n // data.pricing\n this.apiFramework = data.apiFramework;\n\n if (data.creative) {\n this.creativeAdId = data.creative.adId;\n this.creativeId = data.creative.id;\n\n if (data.creative.universalAdId) {\n this.universalAdIdRegistry = data.creative.universalAdId.idRegistry;\n this.universalAdIdValue = data.creative.universalAdId.value;\n }\n }\n this.adDescription = data.adDescription;\n this.minSuggestedDuration = Utils.calculateTimeWithUndefined(data.minSuggestedDuration);\n if (data.survey) {\n this.surveyUrl = data.survey.uri;\n // data.survey.type;\n }\n this.adTitle = data.adTitle;\n this.wrapperAdsCount = data.wrapperAdIds ? data.wrapperAdIds.length : 0;\n }\n }\n const linearAd = ad as LinearAd;\n if (linearAd) {\n this.adSkipAfter = AdSample.parseSkipAfter(linearAd.skippableAfter);\n this.adSkippable = linearAd.skippable || (this.adSkipAfter === undefined ? undefined : this.adSkipAfter >= 0);\n this.adDuration = Utils.calculateTime(linearAd.duration);\n }\n }\n}\n","import {FeatureConfigContainer} from './FeatureConfigContainer';\n\nexport interface LicensingRequest {\n key?: string;\n domain: string;\n version: string;\n}\n\nexport enum LicensingResult {\n Denied = 'denied',\n Granted = 'granted',\n Skip = 'skip',\n}\n\nexport interface LicensingResponse {\n status: LicensingResult;\n message: string;\n features?: FeatureConfigContainer;\n}\n\nexport type LicenseCallFunc = (\n key: string,\n domain: string,\n version: string,\n baseUrl: string,\n) => Promise<LicensingResponse>;\n","export const MESSAGE_NAMESPACE = 'urn:x-cast:com.bitmovin.analytics.cast';\nexport const ANALYTICS_BACKEND_BASE_URL = 'https://analytics-ingress-global.bitmovin.com';\n\nexport const ANALYTICS_LICENSECALL_TIMEOUT = 1000 * 60;\nexport const ANALYTICS_VIDEOSTART_TIMEOUT = 1000 * 60; // in milliseconds\n\nexport const ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD = 50;\nexport const ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL = 60 * 60 * 1000;\n\n/**\n * Time (in milliseconds) of consecutive buffering until a REBUFFER_TIMEOUT_ERROR is raised.\n */\nexport const ANALYTICS_REBUFFER_TIMEOUT = 1000 * 60 * 2;\n\n/**\n * minimal time (in seconds) a seek event should have in order to be recogniced as seek\n */\nexport const ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD = 3;\n\n/**\n * Has to be greater or equal than Ingress side limit (currently 1000).\n */\nexport const SEQUENCE_NUMBER_LIMIT = 1000;\n","import type {PlayerAPI, PlayerConfig} from 'bitmovin-player';\n\nimport type {\n AdapterAPI,\n SsaiAdBreakMetadata,\n SsaiAdMetadata,\n SsaiAdQuartile,\n SsaiAdQuartileMetadata,\n SsaiApi,\n} from '../../api/AdapterAPI';\nimport {Analytics} from '../../core/Analytics';\nimport {\n hasValidSsaiAdBreakMetadataStructure,\n hasValidSsaiAdMetadataStructure,\n hasValidSsaiAdQuartileStructure,\n sanitizeSsaiAdQuartileMetadata,\n simplySanitizeSsaiAdBreakMetadata,\n simplySanitizeSsaiAdMetadata,\n} from '../../core/ssai/ssaiApiUtils';\nimport type {AnalyticsConfig} from '../../types/AnalyticsConfig';\nimport type {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport type {CustomDataValues} from '../../types/CustomDataValues';\nimport {guardAgainstDuplicatedUserId, sanitizeAnalyticsConfig} from '../../utils/analyticsConfigUtils';\nimport {logger} from '../../utils/Logger';\nimport {\n hasPlayerAlreadyBeenAugmented,\n isDefined,\n markPlayerInstanceAsAugmented,\n} from '../../utils/playerAugmentationUtils';\nimport {VERSION} from '../../utils/Version';\nimport type {InternalAdapterAPI} from '../internal/InternalAdapterAPI';\n\nimport {sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition} from './bitmovin8AdapterSsaiApiSanitizeUtils';\nimport {Bitmovin8InternalAdapter} from './Bitmovin8InternalAdapter';\n\nexport class Bitmovin8Adapter implements AdapterAPI {\n private readonly internalAdapter: InternalAdapterAPI | undefined;\n private readonly analytics: Analytics | undefined;\n\n constructor(player: any, opts?: AnalyticsStateMachineOptions) {\n if (hasPlayerAlreadyBeenAugmented(player)) {\n logger.errorMessageToUser('Bitmovin Analytics is already hooked up to this player instance');\n return;\n }\n markPlayerInstanceAsAugmented(player);\n\n const playerConfig: PlayerConfig = (player as PlayerAPI).getConfig();\n const sanitizedConfig = sanitizeAnalyticsConfig(playerConfig.analytics as AnalyticsConfig);\n guardAgainstDuplicatedUserId(sanitizedConfig);\n sanitizedConfig.playerKey = sanitizedConfig.playerKey ?? playerConfig.key;\n\n this.internalAdapter = Bitmovin8InternalAdapter.create(player, opts);\n this.analytics = Analytics.create(sanitizedConfig, this.internalAdapter);\n\n // We do this here in order to put the reference of the adapter onto the player\n // customer using the bitmovin adapter standalone might not know that they need to\n // hold a reference\n player.analytics = this;\n\n this.wrapPlayerLoad(player, this.analytics);\n }\n\n readonly ssai: SsaiApi = {\n adBreakStart: (adBreakMetadata?: SsaiAdBreakMetadata) => {\n if (!isDefined(this.internalAdapter)) return;\n\n // quick fix for v2.39.0 missing validation of adPosition\n const adBreakMetadataWithValidAdPosition = sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition(adBreakMetadata);\n\n if (!hasValidSsaiAdBreakMetadataStructure(adBreakMetadataWithValidAdPosition)) {\n // if we don't have valid ad break metadata, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedAdBreakMetadata = simplySanitizeSsaiAdBreakMetadata(adBreakMetadataWithValidAdPosition);\n\n this.internalAdapter.ssaiService.adBreakStart(sanitizedAdBreakMetadata);\n },\n\n adStart: (adMetadata?: SsaiAdMetadata) => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n if (!hasValidSsaiAdMetadataStructure(adMetadata)) {\n // if we don't have valid ad metadata, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedAdMetadata = simplySanitizeSsaiAdMetadata(adMetadata);\n\n this.internalAdapter.ssaiService.adStart(sanitizedAdMetadata);\n // we need to call this here to revert the customData values to the values before the adBreak\n // this is mainly needed to have clear transitions between ads, and we don't\n // copy over customData values from the first ad into the second ad\n // the adMetadata is applied after this call in the manipulate method when a sample is sent\n // it is a bit of a hack, but it is necessary right now due to the way how samples are created\n this.analytics.setConfigParameters();\n this.analytics.setAutoDetectedDeviceInformation();\n },\n\n adQuartileFinished: (adQuartile: SsaiAdQuartile, adQuartileMetadata?: SsaiAdQuartileMetadata) => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n if (!hasValidSsaiAdQuartileStructure(adQuartile)) {\n // if we don't have valid ad quartile, we don't want to proceed and use SSAI API\n return;\n }\n\n const sanitizedSsaiAdQuartileMetadata = sanitizeSsaiAdQuartileMetadata(adQuartileMetadata);\n\n this.internalAdapter.ssaiService.adQuartileFinished(adQuartile, sanitizedSsaiAdQuartileMetadata);\n },\n\n adBreakEnd: () => {\n if (!isDefined(this.analytics)) return;\n if (!isDefined(this.internalAdapter)) return;\n\n this.internalAdapter.ssaiService.adBreakEnd();\n // we need to call this here to revert the customData values to the values we had before the ad\n this.analytics.setConfigParameters();\n this.analytics.setAutoDetectedDeviceInformation();\n },\n };\n\n /*\n * intercept `player.load` with automated sourceChange handling\n */\n private wrapPlayerLoad(player: PlayerAPI, analytics: Analytics) {\n const originalLoad = player.load;\n player.load = (...args: Parameters<typeof player.load>): Promise<void> => {\n if (args.length > 0) {\n const analyticsConfig = (args[0] as any).analytics;\n // we reset the analytics and reload with a new config\n analytics.sourceChange(analyticsConfig);\n }\n\n return originalLoad.apply(player, args);\n };\n }\n\n static readonly version: string = VERSION;\n\n get version(): string {\n return VERSION;\n }\n\n getCurrentImpressionId(): string | undefined {\n if (!isDefined(this.analytics)) return;\n\n return this.analytics.getCurrentImpressionId();\n }\n\n getUserId(): string | undefined {\n if (!isDefined(this.analytics)) return;\n\n return this.analytics.getUserId();\n }\n\n setCustomData(values: CustomDataValues) {\n if (!isDefined(this.internalAdapter)) return;\n\n this.internalAdapter.setCustomData(values);\n }\n\n setCustomDataOnce(values: CustomDataValues) {\n if (!isDefined(this.analytics)) return;\n\n this.analytics.setCustomDataOnce(values);\n }\n\n sourceChange(config: AnalyticsConfig) {\n if (!isDefined(this.analytics)) return;\n\n this.analytics.sourceChange(config);\n }\n}\n","import type {VideoStartFailedReason} from '../enums/VideoStartFailedReason';\n\nimport type {AnalyticsConfig} from './AnalyticsConfig';\nimport type {AnalyticsEventBase, CustomDataValuesEvent, ErrorEvent} from './EventData';\nimport type {Sample} from './Sample';\n\nexport type HeartbeatPayload = {\n buffered?: Sample['buffered'];\n played?: Sample['played'];\n /** Flag indicating that the event was triggered by SSAI */\n triggeredBySsai?: boolean;\n};\n\nexport interface StateMachineCallbacks {\n setup: (duration: number, state: string) => void;\n startup: (duration: number, state: string) => void;\n playing: (duration: number, state: string) => void;\n heartbeat: (duration: number, state: 'playing' | 'rebuffering', payload: HeartbeatPayload) => void;\n qualitychange: (duration: number, state: string) => void;\n qualitychange_pause: (duration: number, state: string) => void;\n qualitychange_rebuffering: (duration: number, state: string) => void;\n videoChange: (event: any) => void;\n audioChange: (event: any) => void;\n audiotrack_changing: () => void;\n pause: (duration: number, state: string) => void;\n /**\n * Should send a sample with `state: \"seeking\"` and `duration` set to the duration of the seeking.\n */\n seeking: (duration: number) => void;\n /**\n * @deprecated use {@link StateMachineCallbacks.seeking} instead. We should send the samples with `state: \"seeking\"`\n * and not with any custom values like \"paused_seeking\" / \"play_seeking\" / \"seeked\" etc.!\n */\n paused_seeking: (duration: number, state: string) => void;\n /**\n * @deprecated use {@link StateMachineCallbacks.seeking} instead. We should send the samples with `state: \"seeking\"`\n * and not with any custom values like \"paused_seeking\" / \"play_seeking\" / \"seeked\" etc.!\n */\n end_play_seeking: (duration: number, state: string) => void;\n rebuffering: (duration: number, state: string) => void;\n error: (event: Readonly<ErrorEvent>) => void;\n end: (duration: number, state: string) => void;\n unload: (duration: number, state: string) => void;\n ad: (duration: number, state: string) => void;\n mute: () => void;\n unMute: () => void;\n subtitle_changing: () => void;\n setVideoTimeEndFromEvent: (analyticsEventBase: AnalyticsEventBase) => void;\n setVideoTimeStartFromEvent: (analyticsEventBase: AnalyticsEventBase) => void;\n videoStartFailed: (duration: number, reason: VideoStartFailedReason) => void;\n startCasting: (duration: number, event: any) => void;\n casting: (duration: number, event: any) => void;\n manualSourceChange: (event: {config: AnalyticsConfig}) => void;\n initialSourceChange: (event: {config: AnalyticsConfig}) => void;\n muting_ready: (duration: number, state: string, event: any) => void;\n /**\n * Should change {@link CustomDataValues} of analytics module.\n *\n * @remarks\n *\n * It is called via the default \"onleavestate\" state machine callback, and because of that:\n * - it has to match the state name \"CUSTOMDATACHANGE\"\n * - each parameter has to of `undefined` type (unintentionally, it can be called at any time, from any state)\n */\n customdatachange: (\n duration: number | undefined,\n state: string | undefined,\n eventData: CustomDataValuesEvent | undefined,\n ) => void;\n\n /** shuts down the collection and removes/clears all timeouts, intervals, event listeners */\n release: () => void;\n}\n\n/**\n * {@link StateMachineCallbacks} object with each callback set to be empty function (doing nothing).\n *\n * Why?:\n * We need to set it as default value in {@link InternalAdapter} for use case, when {@link InternalAdapter}\n * is already created and listen to player events, but {@link Analytics} was not instantiated/initialized yet (that\n * should set correct {@link StateMachineCallbacks} implementation)\n */\nexport const defaultStateMachineCallbacks: StateMachineCallbacks = {\n setup: () => {},\n startup: () => {},\n playing: () => {},\n heartbeat: () => {},\n qualitychange: () => {},\n qualitychange_pause: () => {},\n qualitychange_rebuffering: () => {},\n videoChange: () => {},\n audioChange: () => {},\n audiotrack_changing: () => {},\n pause: () => {},\n seeking: () => {},\n paused_seeking: () => {},\n end_play_seeking: () => {},\n rebuffering: () => {},\n error: () => {},\n end: () => {},\n unload: () => {},\n ad: () => {},\n mute: () => {},\n unMute: () => {},\n subtitle_changing: () => {},\n setVideoTimeEndFromEvent: () => {},\n setVideoTimeStartFromEvent: () => {},\n videoStartFailed: () => {},\n startCasting: () => {},\n casting: () => {},\n manualSourceChange: () => {},\n initialSourceChange: () => {},\n muting_ready: () => {},\n customdatachange: () => {},\n release: () => {},\n};\n","import type {CodecInfo} from '../types/CodecInfo';\nimport type {PlaybackInfo} from '../types/PlaybackInfo';\nimport {isBlank} from '../utils/stringUtils';\nimport {isNotNullish} from '../utils/Utils';\n\n/**\n * This class is used to store source specific information for the player\n * mainly as a fallback if sourceInfo cannot be determined by the player since the source is already unloaded\n */\nexport class SourceInfoFallbackService {\n private streamFormat: PlaybackInfo['streamFormat'];\n private audioCodec: PlaybackInfo['audioCodec'];\n private videoCodec: PlaybackInfo['videoCodec'];\n\n reset() {\n this.streamFormat = undefined;\n this.audioCodec = undefined;\n this.videoCodec = undefined;\n }\n\n setStreamFormat(streamFormat: PlaybackInfo['streamFormat']) {\n this.streamFormat = streamFormat;\n }\n\n applyStreamFormat(playbackInfo: PlaybackInfo) {\n if (isBlank(this.streamFormat)) {\n return;\n }\n playbackInfo.streamFormat = this.streamFormat;\n }\n\n /**\n * Apply fallback values to {@link PlaybackInfo} if available.\n * If provided {@link CodecInfo} values are available, we store them as new fallback values, before we apply them.\n */\n applyAndStoreCodecInfo(playbackInfo: PlaybackInfo, codecInfo: CodecInfo | undefined) {\n if (isNotNullish(codecInfo?.audioCodec)) {\n this.audioCodec = codecInfo.audioCodec;\n }\n if (isNotNullish(codecInfo?.videoCodec)) {\n this.videoCodec = codecInfo.videoCodec;\n }\n\n if (!isBlank(this.audioCodec)) {\n playbackInfo.audioCodec = this.audioCodec;\n }\n if (!isBlank(this.videoCodec)) {\n playbackInfo.videoCodec = this.videoCodec;\n }\n }\n}\n","declare global {\n /** Variable is defined by webpack.DefinePlugin during the build process. */\n const __VERSION__: string;\n}\n\nexport const VERSION: string = __VERSION__;\n","export const setCookie = (\n name: string,\n value: string,\n attributes?: {domain?: string; expires?: string; maxAge?: number},\n): void => {\n let newCookie = name + '=' + value + '; path=/';\n\n if (attributes?.domain) {\n newCookie += `; domain=${attributes.domain}`;\n }\n\n if (attributes?.expires) {\n newCookie += `; expires=${attributes.expires}`;\n }\n\n if (attributes?.maxAge) {\n newCookie += `; max-age=${attributes.maxAge}`;\n }\n\n document.cookie = newCookie;\n};\n\n/** @see https://www.w3schools.com/js/js_cookies.asp */\nexport const getCookie = (cname: string): string => {\n const name = cname + '=';\n const allCookies = document.cookie.split(';');\n for (const c of allCookies) {\n let cookie = c;\n while (cookie.charAt(0) === ' ') {\n cookie = cookie.substring(1); //trim spaces (if any) between ';' and next attribute\n }\n if (cookie.indexOf(name) === 0) {\n return cookie.substring(name.length, c.length);\n }\n }\n return '';\n};\n\n/** @see https://www.w3schools.com/js/js_cookies.asp */\nexport const deleteCookie = (cname: string): void => {\n document.cookie = `${cname}=; expires=Thu, 01 Jan 1970 00:00:00 UTC; path=/;`;\n};\n","import {PAGE_LOAD_TYPE} from '../enums/PageLoadType';\nimport type {CustomDataValues} from '../types/CustomDataValues';\nimport * as CustomDataUtils from '../types/CustomDataValues';\n\nimport {endsWith, startsWith} from './stringUtils';\n\n/**\n * Performs a loose equality check (==), which means it checks for both null and undefined.\n *\n * @returns {value is null | undefined} `true` if the given value is `null` or `undefined`.\n */\nexport const isNullish = (value: unknown): value is null | undefined => value == null;\n\n/**\n *\n * @returns {value is Exclude<unknown, null | undefined>} `true` if the given value is not `null` and is not `undefined`.\n */\nexport const isNotNullish = <T = unknown>(value: T): value is Exclude<T, null | undefined> => !isNullish(value);\n\n/**\n * @returns {value is boolean} `true` if the given value is {@link isNotNullish} and is type of `boolean`.\n */\nexport const isBoolean = (value: unknown): value is boolean => !isNullish(value) && typeof value === 'boolean';\n\nexport const toBoolean = (value: unknown): boolean => Boolean(value).valueOf();\n\n/**\n * @returns {value is number} `true` if the given value is {@link isNotNullish} and is type of `number`.\n */\nexport const isNumber = (value: unknown): value is number => !isNullish(value) && typeof value === 'number';\n\n/**\n * Checks if a value is a non-null object.\n *\n * We must exclude `null` explicitly, because `typeof null === \"object\"`\n *\n * @returns {value is Record<string, unknown>} `true` if the value is a non-null object, otherwise `false`.\n */\nexport const isObject = <T extends object>(value: T): value is T => {\n return isNotNullish(value) && typeof value === 'object';\n};\n\n/**\n * Checks if a value is a plain object (not an array, function, or built-in instance).\n *\n * @returns {value is Record<string, unknown>} `true` if the value is a plain object, otherwise `false`.\n */\nexport const isPlainObject = <T extends object>(value: T): value is T => {\n return Object.prototype.toString.call(value) === '[object Object]';\n};\n\nexport const sanitizePath = (path: string): string => {\n return path.replace(/\\/$/g, '');\n};\n\n/** Take a time in seconds and return a value that represents a time in milliseconds, rounded to the nearest integer */\nexport const calculateTime = (timeInSeconds: number) => Math.round(timeInSeconds * 1000);\n\n/** Same as {@link calculateTime} but if time is \"nullish\", then the return value is `undefined` */\nexport const calculateTimeWithUndefined = (timeInSeconds: number | null | undefined): number | undefined => {\n if (isNullish(timeInSeconds)) {\n return undefined;\n }\n return calculateTime(timeInSeconds);\n};\n\n/**\n * @deprecated Use directly `Date.now()` instead\n *\n * Return the current time in milliseconds.\n */\nexport const getCurrentTimestamp = (): number => {\n return Date.now();\n};\n\n/**\n * Empty function returns undefined\n *\n * @deprecated\n */\nexport const noOp = () => undefined;\n\nexport const getCustomDataString = (customData: any): string | undefined => {\n if (typeof customData === 'object') {\n return JSON.stringify(customData);\n } else if (typeof customData === 'function') {\n return getCustomDataString(customData());\n } else if (typeof customData === 'undefined') {\n return customData;\n } else if (typeof customData !== 'string') {\n return String(customData);\n }\n\n return customData;\n};\n\nexport const transferCustomDataFields = (fromConfig: CustomDataValues, toConfig: CustomDataValues) => {\n for (let i = 1; i <= CustomDataUtils.customDataFieldCount; i++) {\n const customDataField = `customData${i}`;\n toConfig[customDataField] = getCustomDataString(fromConfig[customDataField]);\n }\n};\n\nexport const getDocumentPropWithPrefix = (prop: string): string | undefined => {\n const prefixes = ['webkit', 'moz', 'ms', 'o'];\n if (prop in document) {\n return prop;\n }\n\n const pascalCase = prop.charAt(0).toUpperCase() + prop.slice(1);\n for (const prefix of prefixes) {\n if (prefix + pascalCase in document) {\n return prefix + pascalCase;\n }\n }\n return undefined;\n};\n\nexport const isVideoInFullscreen = () => {\n const fullscreenProp = getDocumentPropWithPrefix('fullscreenElement');\n return fullscreenProp !== undefined && document[fullscreenProp] && document[fullscreenProp].nodeName === 'VIDEO';\n};\n\nexport const getHiddenProp = (): string | undefined => {\n return getDocumentPropWithPrefix('hidden');\n};\n\nexport function getPageLoadType(): PAGE_LOAD_TYPE {\n const hiddenProp = getHiddenProp();\n if (isNotNullish(hiddenProp) && document[hiddenProp] === true) {\n return PAGE_LOAD_TYPE.BACKGROUND;\n }\n return PAGE_LOAD_TYPE.FOREGROUND;\n}\n\nexport const getHostnameAndPathFromUrl = (url: string) => {\n const domElement = document.createElement('a');\n domElement.href = url;\n\n return {hostname: domElement.hostname, path: domElement.pathname};\n};\n\nexport const calculatePercentage = (numerator?: number, denominator?: number): number | undefined => {\n if (denominator === undefined || denominator === 0) {\n return undefined;\n }\n return Math.round(((numerator || 0) / denominator) * 100);\n};\n\nexport const getURLResourceName = (url: string): string => {\n if (url.length === 0) {\n return '';\n }\n return url.split('/').pop() || '';\n};\n\nexport const joinUrls = (...args: string[]): string => {\n return args.reduce((prev, current) => {\n const prevUrlValue = endsWith(prev, '/') && current !== undefined ? prev.substr(0, prev.length - 1) : prev;\n const nextUrlValue = startsWith(current, '/') ? current.substr(1) : current;\n return prevUrlValue + '/' + nextUrlValue;\n });\n};\n","import {ProgressiveSourceConfig} from '../types/ProgressiveSourceConfig';\nimport {ProgressiveSourceInfo} from '../types/SourceInfo';\n\nimport {isNotNullish} from './Utils';\n\nexport const getSourceInfoFromBitmovinSourceConfig = (\n progressive: ProgressiveSourceConfig,\n player: any,\n): ProgressiveSourceInfo => {\n if (!progressive) {\n return {\n progBitrate: undefined,\n progUrl: undefined,\n };\n }\n\n if (typeof progressive === 'string') {\n return {\n progBitrate: 0,\n progUrl: progressive,\n };\n }\n\n if (Array.isArray(progressive) && progressive.length > 0) {\n const playbackVideoData = player.getPlaybackVideoData();\n let progressiveArrayIndex = 0;\n\n if (isNotNullish(playbackVideoData) && !isNaN(+playbackVideoData.id)) {\n progressiveArrayIndex = +playbackVideoData.id;\n }\n\n return {\n progBitrate: progressive[progressiveArrayIndex].bitrate || 0,\n progUrl: progressive[progressiveArrayIndex].url,\n };\n }\n\n if (typeof progressive === 'object' && !Array.isArray(progressive)) {\n return {\n progBitrate: progressive.bitrate || 0,\n progUrl: progressive.url,\n };\n }\n\n return {\n progBitrate: undefined,\n progUrl: undefined,\n };\n};\n","import {LicensingResponse} from '../types/LicensingRequest';\n\nimport {post} from './Http';\nimport {joinUrls} from './Utils';\n\nexport function LicenseCall(key: string, domain: string, version: string, baseUrl: string): Promise<LicensingResponse> {\n const licenseServerUrl = joinUrls(baseUrl, '/licensing');\n const licensingRequest = {\n analyticsVersion: version,\n domain,\n key,\n };\n\n return new Promise<LicensingResponse>((resolve) => {\n post(licenseServerUrl, licensingRequest, (response) => {\n resolve(response);\n });\n });\n}\n","import {appendSsaiRoutingParam, isSsaiRelatedSample} from '../core/ssai/ssaiUtils';\nimport type {AdSample, Sample} from '../types/Sample';\n\nimport {post} from './Http';\nimport {joinUrls, noOp} from './Utils';\n\nexport class AnalyticsCall {\n private readonly analyticsServerUrl: string;\n private readonly adAnalyticsServerUrl: string;\n\n constructor(baseUrl: string) {\n this.analyticsServerUrl = joinUrls(baseUrl, 'analytics');\n this.adAnalyticsServerUrl = joinUrls(baseUrl, 'analytics/a');\n }\n\n sendRequest(sample: Sample, callback: () => void) {\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n post(analyticsUrl, sample, callback);\n }\n\n sendUnloadRequest(sample: Sample) {\n const sendBeaconFallback = (data: Sample) => this.sendRequestSynchronous(data, noOp);\n\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n this.trySendBeacon(sendBeaconFallback, analyticsUrl, sample);\n }\n\n private trySendBeacon(\n fallbackFunction: (data: any) => void,\n url: string,\n data: unknown,\n requestHeaders: {[headerName: string]: string} = {},\n ) {\n if (typeof navigator.sendBeacon === 'undefined') {\n fallbackFunction(data);\n } else {\n /**\n * With a Blob we can send payload but also http headers\n * @see https://stackoverflow.com/questions/40523469/navigator-sendbeacon-to-pass-header-information\n */\n const blob = new Blob([JSON.stringify(data)], requestHeaders);\n const success = navigator.sendBeacon(url, blob);\n if (!success) {\n fallbackFunction(data);\n }\n }\n }\n\n sendRequestSynchronous(sample: Sample, callback: () => void) {\n let analyticsUrl = this.analyticsServerUrl;\n if (isSsaiRelatedSample(sample)) {\n analyticsUrl = appendSsaiRoutingParam(analyticsUrl);\n }\n\n post(analyticsUrl, sample, callback, false);\n }\n\n sendAdRequest(adSample: AdSample) {\n let adAnalyticsUrl = this.adAnalyticsServerUrl;\n if (isSsaiRelatedSample(adSample)) {\n adAnalyticsUrl = appendSsaiRoutingParam(adAnalyticsUrl);\n }\n\n const sendBeaconFallback = (data: AdSample) => post(adAnalyticsUrl, data, noOp);\n this.trySendBeacon(sendBeaconFallback, adAnalyticsUrl, adSample);\n }\n}\n","export class AdCallbacks {\n onAdStarted = (_event: any): void => undefined;\n onAdFinished = (_event: any): void => undefined;\n onAdBreakStarted = (_event: any): void => undefined;\n onAdBreakFinished = (_event: any): void => undefined;\n onAdClicked = (_event: any): void => undefined;\n onAdError = (_event: any): void => undefined;\n onAdManifestLoaded = (_event: any): void => undefined;\n onAdQuartile = (_event: any): void => undefined;\n onAdSkipped = (_event: any): void => undefined;\n onPlay = (_issuer?: string): void => undefined;\n onPause = (_issuer?: string): void => undefined;\n onBeforeUnload = (): void => undefined;\n}\n\nexport interface AdModuleAPI {\n readonly adCallbacks: AdCallbacks;\n isLinearAdActive: () => boolean;\n getContainer: () => HTMLElement;\n getAdModuleInfo: () => {name?: string; version?: string};\n currentTime: () => number;\n}\n","export interface CustomDataValues {\n customData1?: string;\n customData2?: string;\n customData3?: string;\n customData4?: string;\n customData5?: string;\n customData6?: string;\n customData7?: string;\n customData8?: string;\n customData9?: string;\n customData10?: string;\n customData11?: string;\n customData12?: string;\n customData13?: string;\n customData14?: string;\n customData15?: string;\n customData16?: string;\n customData17?: string;\n customData18?: string;\n customData19?: string;\n customData20?: string;\n customData21?: string;\n customData22?: string;\n customData23?: string;\n customData24?: string;\n customData25?: string;\n customData26?: string;\n customData27?: string;\n customData28?: string;\n customData29?: string;\n customData30?: string;\n customData31?: string;\n customData32?: string;\n customData33?: string;\n customData34?: string;\n customData35?: string;\n customData36?: string;\n customData37?: string;\n customData38?: string;\n customData39?: string;\n customData40?: string;\n customData41?: string;\n customData42?: string;\n customData43?: string;\n customData44?: string;\n customData45?: string;\n customData46?: string;\n customData47?: string;\n customData48?: string;\n customData49?: string;\n customData50?: string;\n experimentName?: string;\n}\n\n/**\n * Lists all keys of the {@see CustomDataValues} interface.\n */\nexport const customDataValuesKeys: Array<keyof CustomDataValues> = [\n 'customData1',\n 'customData2',\n 'customData3',\n 'customData4',\n 'customData5',\n 'customData6',\n 'customData7',\n 'customData8',\n 'customData9',\n 'customData10',\n 'customData11',\n 'customData12',\n 'customData13',\n 'customData14',\n 'customData15',\n 'customData16',\n 'customData17',\n 'customData18',\n 'customData19',\n 'customData20',\n 'customData21',\n 'customData22',\n 'customData23',\n 'customData24',\n 'customData25',\n 'customData26',\n 'customData27',\n 'customData28',\n 'customData29',\n 'customData30',\n 'customData31',\n 'customData32',\n 'customData33',\n 'customData34',\n 'customData35',\n 'customData36',\n 'customData37',\n 'customData38',\n 'customData39',\n 'customData40',\n 'customData41',\n 'customData42',\n 'customData43',\n 'customData44',\n 'customData45',\n 'customData46',\n 'customData47',\n 'customData48',\n 'customData49',\n 'customData50',\n\n 'experimentName',\n];\n\n/**\n * The number of CustomDataXX fields in {@see CustomDataValues}.\n */\nexport const customDataFieldCount = customDataValuesKeys.filter((i) => i.match('customData\\\\d+')).length;\n\nexport const extractCustomDataFieldsOnly = (input: CustomDataValues): CustomDataValues => {\n const retVal: CustomDataValues = {};\n customDataValuesKeys.forEach((key) => {\n if (input[key]) {\n retVal[key] = input[key];\n }\n });\n return retVal;\n};\n","export class Converter {\n static bytesToBits(bytes: number): number {\n return bytes * 8;\n }\n static bitsToBytes(bits: number): number {\n return Math.round(bits / 8);\n }\n static kiloBitsToBits(kiloBits: number): number {\n return kiloBits * 1000;\n }\n}\n","import * as Utils from '../utils/Utils';\n\nimport {CustomDataValues} from './CustomDataValues';\nimport {Sample} from './Sample';\n\nexport class AdAnalyticsSample implements CustomDataValues {\n adModule?: string;\n adModuleVersion?: string;\n videoImpressionId?: string;\n userAgent?: string;\n language?: string;\n cdnProvider?: string;\n customData1?: string;\n customData2?: string;\n customData3?: string;\n customData4?: string;\n customData5?: string;\n customData6?: string;\n customData7?: string;\n customData8?: string;\n customData9?: string;\n customData10?: string;\n customData11?: string;\n customData12?: string;\n customData13?: string;\n customData14?: string;\n customData15?: string;\n customData16?: string;\n customData17?: string;\n customData18?: string;\n customData19?: string;\n customData20?: string;\n customData21?: string;\n customData22?: string;\n customData23?: string;\n customData24?: string;\n customData25?: string;\n customUserId?: string;\n experimentName?: string;\n domain?: string;\n key?: string;\n path?: string;\n player?: string;\n playerKey?: string;\n playerTech?: string;\n screenHeight?: number;\n screenWidth?: number;\n version?: string;\n size?: string;\n userId?: string;\n videoId?: string;\n videoTitle?: string;\n videoWindowHeight?: number;\n videoWindowWidth?: number;\n playerStartupTime?: number;\n analyticsVersion?: string;\n pageLoadTime?: number;\n pageLoadType?: number;\n autoplay?: boolean;\n platform = 'web';\n audioCodec?: string;\n videoCodec?: string;\n\n constructor(sample?: Sample) {\n if (!sample) {\n return;\n }\n this.videoImpressionId = sample.impressionId;\n this.userAgent = sample.userAgent;\n this.language = sample.language;\n this.cdnProvider = sample.cdnProvider;\n\n Utils.transferCustomDataFields(sample, this);\n\n this.customUserId = sample.customUserId;\n this.domain = sample.domain;\n this.experimentName = sample.experimentName;\n this.key = sample.key;\n this.path = sample.path;\n this.player = sample.player;\n this.playerKey = sample.playerKey;\n this.playerTech = sample.playerTech;\n this.screenHeight = sample.screenHeight;\n this.screenWidth = sample.screenWidth;\n this.version = sample.version;\n this.size = sample.size;\n this.userId = sample.userId;\n this.videoId = sample.videoId;\n this.videoTitle = sample.videoTitle;\n this.videoWindowHeight = sample.videoWindowHeight;\n this.videoWindowWidth = sample.videoWindowWidth;\n this.audioCodec = sample.audioCodec;\n this.videoCodec = sample.videoCodec;\n }\n}\n","export enum CastTech {\n AirPlay = 'AirPlay',\n GoogleCast = 'GoogleCast',\n WebSocket = 'WebSocket',\n}\n","import {SegmentInfo} from '../types/SegmentInfo';\n\nexport class SegmentTracker {\n protected segments: SegmentInfo[];\n\n constructor() {\n this.segments = [];\n }\n\n reset(): void {\n this.segments = [];\n }\n\n addSegment(segment: SegmentInfo): void {\n this.segments.push(segment);\n }\n\n removeSegment(url: string): void {\n this.segments = this.segments.filter((s) => s.url !== url);\n }\n\n getSegments(): SegmentInfo[] {\n return this.segments;\n }\n}\n","import type {\n AdPosition,\n SsaiAdBreakMetadata,\n SsaiAdMetadata,\n SsaiAdQuartile,\n SsaiAdQuartileMetadata,\n} from '../../api/AdapterAPI';\nimport {CustomDataValues, extractCustomDataFieldsOnly} from '../../types/CustomDataValues';\nimport {logger} from '../../utils/Logger';\nimport {isValidString} from '../../utils/stringUtils';\nimport {isNotNullish, isNullish, isPlainObject, transferCustomDataFields} from '../../utils/Utils';\n\nexport function isAdPosition(anything: unknown): anything is AdPosition {\n // invalid, when not defined as one of string values we expect\n return anything === 'preroll' || anything === 'midroll' || anything === 'postroll';\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdBreakMetadataStructure(\n anything: unknown,\n): anything is SsaiAdBreakMetadata | null | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(anything)) return true;\n\n // invalid, when value was defined, but not as a plain object\n if (!isPlainObject(anything as object)) {\n logger.errorMessageToUser('Invalid SsaiAdBreakMetadata: not a plain object');\n return false;\n }\n\n const maybeSsaiAdBreakMetadata = anything as SsaiAdBreakMetadata;\n\n // invalid, when `adPosition` was defined, but not as an ad position string we expect\n if (isNotNullish(maybeSsaiAdBreakMetadata.adPosition) && !isAdPosition(maybeSsaiAdBreakMetadata.adPosition)) {\n logger.errorMessageToUser(\"Invalid SsaiAdBreakMetadata: 'adPosition' property is not valid\");\n return false;\n }\n\n return true;\n}\n\n/**\n * Simple sanitization of {@link SsaiAdBreakMetadata} without object structure check,\n * because {@link hasValidSsaiAdBreakMetadataStructure} should be called before in adapter SSAI API function!\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return `undefined`\n * - recreate a new object to avoid side effects by using same reference from outside\n *\n * @param adBreakMetadata SsaiAdBreakMetadata or `undefined` (optional SSAI API parameter)\n */\nexport function simplySanitizeSsaiAdBreakMetadata(\n adBreakMetadata: SsaiAdBreakMetadata | undefined,\n): SsaiAdBreakMetadata | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(adBreakMetadata)) {\n // sanitize to use `undefined` in code\n return undefined;\n }\n\n // recreate a new object\n return {\n adPosition: adBreakMetadata.adPosition,\n };\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdMetadataStructure(anything: unknown): anything is SsaiAdMetadata | null | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(anything)) {\n return true;\n }\n\n // invalid, when value was defined, but not as a plain object\n if (!isPlainObject(anything as object)) {\n logger.errorMessageToUser('Invalid SsaiAdMetadata: not a plain object');\n return false;\n }\n\n const maybeSsaiAdMetadata = anything as SsaiAdMetadata;\n\n // invalid, when `adId` was defined, but not as a string\n if (isNotNullish(maybeSsaiAdMetadata.adId) && !isValidString(maybeSsaiAdMetadata.adId)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'adId' property is not string\");\n return false;\n }\n\n // invalid, when `adSystem` was defined, but not as a string\n if (isNotNullish(maybeSsaiAdMetadata.adSystem) && !isValidString(maybeSsaiAdMetadata.adSystem)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'adSystem' property is not string\");\n return false;\n }\n\n // invalid, when `customData` was defined, but not as an object\n if (isNotNullish(maybeSsaiAdMetadata.customData) && !isPlainObject(maybeSsaiAdMetadata.customData)) {\n logger.errorMessageToUser(\"Invalid SsaiAdMetadata: 'customData' property is not a plain object\");\n return false;\n }\n\n return true;\n}\n\n/**\n * Simple sanitization of {@link SsaiAdMetadata} without object structure check,\n * because {@link hasValidSsaiAdMetadataStructure} should be called before in adapter SSAI API function!\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return `undefined`\n * - recreate a new object to avoid side effects by using same reference from outside\n *\n * @param ssaiAdMetadata SsaiAdMetadata or `undefined` (optional SSAI API parameter)\n */\nexport function simplySanitizeSsaiAdMetadata(ssaiAdMetadata: SsaiAdMetadata | undefined): SsaiAdMetadata | undefined {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n if (isNullish(ssaiAdMetadata)) {\n // sanitize to use `undefined` in code\n return undefined;\n }\n\n let sanitizedCustomDataValues: CustomDataValues | undefined = undefined;\n\n // we are extracting the customData fields explicitly to make sure that there is not a different object passed\n if (isNotNullish(ssaiAdMetadata.customData)) {\n const extracted = extractCustomDataFieldsOnly(ssaiAdMetadata.customData);\n sanitizedCustomDataValues = {};\n transferCustomDataFields(extracted, sanitizedCustomDataValues);\n }\n\n // recreate a new object\n return {\n adId: ssaiAdMetadata.adId,\n adSystem: ssaiAdMetadata.adSystem,\n customData: sanitizedCustomDataValues,\n };\n}\n\nexport function isSsaiAdQuartile(anything: unknown): anything is SsaiAdQuartile {\n return anything === 'first' || anything === 'midpoint' || anything === 'third' || anything === 'completed';\n}\n\n/** User SSAI API input validation */\nexport function hasValidSsaiAdQuartileStructure(anything: unknown): anything is SsaiAdQuartile {\n if (!isSsaiAdQuartile(anything)) {\n logger.errorMessageToUser('Invalid SsaiAdQuartile');\n return false;\n }\n\n return true;\n}\n\n/**\n * Full sanitization of unknown customer input.\n * We sanitize correct object structure and print user error messages for incorrect input.\n *\n * Sanitization:\n * - if `undefined/null` is passed, it will return empty object `{}`\n * - if NOT `typeof 'object'` is passed, it will return empty object `{}` and print user error message\n * - recreate a new object to avoid side effects by using same reference from outside\n * - if `failedBeaconUrl` is not valid string, we use `undefined` and print user error message\n * - if `failedBeaconUrl` is longer than 500 characters, we cut it\n *\n * @param anything Can be anything, as it is coming from customer JavaScript code\n */\nexport function sanitizeSsaiAdQuartileMetadata(anything: unknown): SsaiAdQuartileMetadata {\n if (isNullish(anything)) {\n // \"nullish\" is considered to be valid (SSAI API parameter is optional)\n // sanitize to plain object to not use nullish value in code\n return {};\n }\n\n if (!isPlainObject(anything as object)) {\n // if NOT a plain object, we return empty plain object and print user error message\n logger.errorMessageToUser('Invalid SsaiAdQuartileMetadata: not a plain object');\n return {};\n }\n\n const maybeSsaiAdQuartileMetadata = anything as SsaiAdQuartileMetadata;\n\n // recreate a new object\n const ssaiAdQuartileMetadata: SsaiAdQuartileMetadata = {\n failedBeaconUrl: maybeSsaiAdQuartileMetadata.failedBeaconUrl,\n };\n\n if (!isValidString(ssaiAdQuartileMetadata.failedBeaconUrl)) {\n logger.errorMessageToUser(\"Invalid SsaiAdQuartileMetadata: 'failedBeaconUrl' property is not string\");\n ssaiAdQuartileMetadata.failedBeaconUrl = undefined;\n } else {\n ssaiAdQuartileMetadata.failedBeaconUrl = ssaiAdQuartileMetadata.failedBeaconUrl.substring(0, 500);\n }\n\n return ssaiAdQuartileMetadata;\n}\n","import type {\n AudioPlaybackQualityChangedEvent,\n PlayerAPI,\n PlayerEventBase,\n SeekEvent,\n UserInteractionEvent,\n VideoPlaybackQualityChangedEvent,\n} from 'bitmovin-player';\n\nimport {Bitmovin8AnalyticsStateMachine} from '../../analyticsStateMachines/bitmovin8/Bitmovin8AnalyticsStateMachine';\nimport {Analytics} from '../../core/Analytics';\nimport {DownloadSpeedMeter} from '../../core/DownloadSpeedMeter';\nimport {HeartbeatService} from '../../core/HeartbeatService';\nimport {SegmentTracker} from '../../core/SegmentTracker';\nimport {SourceInfoFallbackService} from '../../core/SourceInfoFallbackService';\nimport VideoCompletionTracker from '../../core/VideoCompletionTracker';\nimport {CastTech} from '../../enums/CastTech';\nimport {ErrorCode} from '../../enums/ErrorCode';\nimport {Event} from '../../enums/Event';\nimport {Player} from '../../enums/Player';\nimport {PlayerSize} from '../../enums/PlayerSize';\nimport {ErrorDetailBackend} from '../../features/errordetails/ErrorDetailBackend';\nimport {ErrorDetailTracking} from '../../features/errordetails/ErrorDetailTracking';\nimport {Feature} from '../../features/Feature';\nimport {FeatureConfig} from '../../features/FeatureConfig';\nimport {HttpRequestTracking} from '../../features/httprequesttracking/HttpRequestTracking';\nimport {AnalyticsConfig} from '../../types/AnalyticsConfig';\nimport {AnalyticsStateMachineOptions} from '../../types/AnalyticsStateMachineOptions';\nimport {DownloadSpeedInfo} from '../../types/DownloadSpeedInfo';\nimport {DrmPerformanceInfo} from '../../types/DrmPerformanceInfo';\nimport type {AnalyticsEventBase} from '../../types/EventData';\nimport {FeatureConfigContainer} from '../../types/FeatureConfigContainer';\nimport {normalizeVideoDuration, PlaybackInfo} from '../../types/PlaybackInfo';\nimport {SegmentInfo} from '../../types/SegmentInfo';\nimport {getSourceInfoFromBitmovinSourceConfig} from '../../utils/BitmovinProgressiveSourceHelper';\nimport {logger} from '../../utils/Logger';\nimport * as AnalyticsSettings from '../../utils/Settings';\nimport {isNotNullish, isNullish} from '../../utils/Utils';\nimport {AdModuleAPI} from '../internal/ads/AdModuleAPI';\nimport {InternalAdapter} from '../internal/InternalAdapter';\nimport {InternalAdapterAPI} from '../internal/InternalAdapterAPI';\n\nimport {Bitmovin8AdModule} from './Bitmovin8AdModule';\nimport {HttpRequestTrackingAdapter} from './player/HttpRequestTrackingAdapter';\nimport {SegmentTrackerAdapter} from './player/SegmentTrackerAdapter';\nimport {SpeedMeterAdapter} from './player/SpeedMeterAdapter';\n\nenum ViewMode {\n Fullscreen = 'fullscreen',\n Inline = 'inline',\n PictureInPicture = 'pictureinpicture',\n}\n\nexport class Bitmovin8InternalAdapter extends InternalAdapter implements InternalAdapterAPI {\n override get downloadSpeedInfo(): DownloadSpeedInfo {\n return this.speedMeter.getInfo();\n }\n\n override get segments(): SegmentInfo[] {\n return this.segmentTracker.getSegments();\n }\n\n get adModule(): AdModuleAPI | undefined {\n return this._adModule;\n }\n\n get supportsDeferredLicenseLoading(): boolean {\n return true;\n }\n\n /** Boolean flag to prevent multiple calls of the {@link Event.UNLOAD} event */\n private onBeforeUnLoadEvent = false;\n private _adModule?: AdModuleAPI;\n private lastTrackedCurrentTime: number | undefined;\n private videoDuration: number | undefined;\n\n constructor(\n private player: PlayerAPI,\n private speedMeter: DownloadSpeedMeter,\n private segmentTracker: SegmentTracker,\n readonly videoCompletionTracker: VideoCompletionTracker,\n private httpRequestTrackingAdapter: HttpRequestTrackingAdapter,\n sourceInfoFallbackService: SourceInfoFallbackService,\n opts?: AnalyticsStateMachineOptions,\n ) {\n super(opts);\n const playingHeartbeatService = new HeartbeatService(() => player.getCurrentTime());\n const stateMachine = new Bitmovin8AnalyticsStateMachine(\n this.stateMachineCallbacks,\n playingHeartbeatService,\n this.opts,\n );\n playingHeartbeatService.setListener(stateMachine);\n this.sourceInfoFallbackService = sourceInfoFallbackService;\n\n this.stateMachine = stateMachine;\n }\n\n protected get currentTime(): number {\n try {\n // during ad this.player.getCurrentTime() returns time of ad and not video\n // this then messes with videotime_start and videotime_end measurements of video\n // we don't track videotimes for ads\n if (isNotNullish(this.player?.getCurrentTime) && !this.isAdPlaying) {\n return this.player.getCurrentTime();\n }\n } catch {\n logger.warn('Analytics Collector attempted to access player, but player is not available anymore');\n }\n return this.lastTrackedCurrentTime ? this.lastTrackedCurrentTime : 0;\n }\n\n protected get isAdPlaying(): boolean {\n const currentAd = this.player.ads && this.player.ads.getActiveAd();\n return isNotNullish(currentAd);\n }\n\n initialize(analytics: Analytics): Array<Feature<FeatureConfigContainer, FeatureConfig>> {\n this.registerPlayerEventListeners();\n this.registerUnloadEventListeners();\n\n this._adModule = new Bitmovin8AdModule(this.player, this.windowEventTracker);\n\n this.ssaiService.activate({\n getPlayerCurrentTime: () => this.currentTime,\n reportEngagementInteraction: (ssaiEngagementInteractionData) => {\n analytics.sendSsaiEngagementAdSample(ssaiEngagementInteractionData);\n },\n reportPlaybackInteraction: (timestamp: number, eventData: AnalyticsEventBase) =>\n this.stateMachine.onSsaiPlaybackInteraction(timestamp, eventData),\n });\n\n const requestTracking = new HttpRequestTracking([this.httpRequestTrackingAdapter]);\n const errorDetailTracking = new ErrorDetailTracking(\n analytics.errorDetailTrackingSettingsProvider,\n new ErrorDetailBackend(analytics.errorDetailTrackingSettingsProvider.collectorConfig),\n [analytics.errorDetailSubscribable],\n requestTracking,\n );\n return [errorDetailTracking];\n }\n\n override clearValues(): void {\n this.speedMeter.reset();\n }\n\n override clearSegments(): void {\n this.segmentTracker.reset();\n }\n\n override resetSourceRelatedState(): void {\n this.ssaiService.resetSourceRelatedState();\n super.resetSourceRelatedState();\n }\n\n getPlayerVersion = () => this.player.version;\n getPlayerName = () => Player.BITMOVIN;\n getPlayerTech = () => this.player.getPlayerType();\n getAutoPlay(): boolean {\n if (this.player.getConfig().playback) {\n return (this.player.getConfig() as any).playback.autoplay || false;\n }\n return false;\n }\n getDrmPerformanceInfo = (): DrmPerformanceInfo | undefined => this.drmPerformanceInfo;\n\n getCurrentPlaybackInfo(): PlaybackInfo {\n const info: PlaybackInfo = {\n ...super.getCommonPlaybackInfo(),\n size: this.player.getViewMode() === ViewMode.Fullscreen ? PlayerSize.Fullscreen : PlayerSize.Window,\n playerTech: this.getPlayerTech(),\n isLive: this.player.isLive(),\n videoDuration: normalizeVideoDuration(this.videoDuration),\n streamFormat: this.player.getStreamType(),\n videoWindowWidth: this.player.getContainer().offsetWidth,\n videoWindowHeight: this.player.getContainer().offsetHeight,\n isMuted: this.player.isMuted(),\n isCasting: this.player.isCasting(),\n audioLanguage: isNotNullish(this.player.getAudio()) ? this.player.getAudio()?.lang : undefined,\n subtitleEnabled: false,\n droppedFrames: isNotNullish(this.player.getSource()) ? this.player.getDroppedVideoFrames() : 0,\n };\n\n this.applySubtitleProperties(info);\n this.applyPlaybackQualityProperties(info);\n this.applyCastingProperties(info);\n this.applySourceProperties(info);\n\n if (isNullish(info.streamFormat) || info.streamFormat === 'unknown') {\n // in case we cannot detect the streamFormat directly from\n // the player, we use the stored streamFormat as a fallback\n this.sourceInfoFallbackService.applyStreamFormat(info);\n }\n\n return info;\n }\n\n sourceChange(config: AnalyticsConfig) {\n this.stateMachine.callManualSourceChangeEvent(config, this.currentTime);\n }\n\n onError(): void {\n this.clearSegments();\n }\n\n private registerPlayerEventListeners() {\n this.player.on(this.player.exports.PlayerEvent.SourceUnloaded, (_event: any) => {\n this.segmentTracker.reset();\n this.eventCallback(Event.SOURCE_UNLOADED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SourceLoaded, (_event: any) => {\n this.videoCompletionTracker.reset();\n this.videoDuration = this.player.getDuration();\n this.videoCompletionTracker.setVideoDuration(this.player.getDuration());\n this.sourceInfoFallbackService.setStreamFormat(this.player.getStreamType());\n this.eventCallback(Event.SOURCE_LOADED, {});\n });\n\n this.player.on(this.player.exports.PlayerEvent.CastStarted, (event: any) => {\n this.eventCallback(Event.START_CAST, event);\n });\n\n this.player.on(this.player.exports.PlayerEvent.CastStopped, () => {\n this.eventCallback(Event.END_CAST, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Play, (e: UserInteractionEvent) => {\n if (e.issuer !== 'ui-seek') {\n this.eventCallback(Event.PLAY, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Playing, (e: UserInteractionEvent) => {\n if (e.issuer !== 'advertising-api') {\n this.eventCallback(Event.PLAYING, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Paused, (e: UserInteractionEvent) => {\n if (e.issuer !== 'ui-seek') {\n this.eventCallback(Event.PAUSE, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.TimeChanged, (_event: PlayerEventBase) => {\n if (!this.isAdPlaying) {\n this.lastTrackedCurrentTime = this.player.getCurrentTime();\n }\n this.eventCallback(Event.TIMECHANGED, {\n currentTime: this.lastTrackedCurrentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Seek, (e: UserInteractionEvent) => {\n if (this.allowSeeking(e)) {\n this.eventCallback(Event.SEEK, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.Seeked, () => {\n this.eventCallback(Event.SEEKED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.StallStarted, () => {\n this.eventCallback(Event.START_BUFFERING, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.StallEnded, () => {\n this.eventCallback(Event.END_BUFFERING, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AudioPlaybackQualityChanged, (eventData) => {\n const audioQualityChangedData = eventData as AudioPlaybackQualityChangedEvent;\n const sourceQuality = audioQualityChangedData.sourceQuality;\n const targetQuality = audioQualityChangedData.targetQuality;\n\n if (isNullish(targetQuality)) {\n return;\n }\n\n // we don't want to track the initial audioQualityChange event thus, we only\n // track the event if the sourceQuality is not null\n if (isNullish(sourceQuality)) {\n this.qualityChangeService.setAudioBitrate(targetQuality.bitrate);\n return;\n }\n\n if (this.qualityChangeService.shouldAllowAudioQualityChange(targetQuality.bitrate)) {\n this.eventCallback(Event.AUDIO_CHANGE, {\n bitrate: targetQuality.bitrate,\n currentTime: this.currentTime,\n codec: (targetQuality as any).codec,\n });\n }\n\n this.qualityChangeService.setAudioBitrate(targetQuality.bitrate);\n });\n\n this.player.on(this.player.exports.PlayerEvent.VideoPlaybackQualityChanged, (eventData) => {\n const videoQualityChangedData = eventData as VideoPlaybackQualityChangedEvent;\n const sourceQuality = videoQualityChangedData.sourceQuality;\n const targetQuality = videoQualityChangedData.targetQuality;\n\n // if targetQuality is null we just ignore the event\n // this is probably and outlier or the end of a session\n // where we don't want to track quality changes\n if (isNullish(targetQuality)) {\n return;\n }\n\n // we don't want to track the initial videoQualityChange event thus, we only\n // track the event if the sourceQuality is not null\n if (isNullish(sourceQuality)) {\n this.qualityChangeService.setVideoBitrate(targetQuality.bitrate);\n return;\n }\n\n if (this.qualityChangeService.shouldAllowVideoQualityChange(targetQuality.bitrate)) {\n this.eventCallback(Event.VIDEO_CHANGE, {\n width: targetQuality.width,\n height: targetQuality.height,\n bitrate: targetQuality.bitrate,\n currentTime: this.currentTime,\n codec: (targetQuality as any).codec,\n });\n }\n\n this.qualityChangeService.setVideoBitrate(targetQuality.bitrate);\n });\n\n this.player.on(this.player.exports.PlayerEvent.ViewModeChanged, (e: any) => {\n if (e.to === 'fullscreen') {\n this.eventCallback(Event.START_FULLSCREEN, {\n currentTime: this.currentTime,\n });\n } else if (e.from === 'fullscreen') {\n this.eventCallback(Event.END_FULLSCREEN, {\n currentTime: this.currentTime,\n });\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdStarted, (_event: any) => {\n this.eventCallback(Event.START_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdFinished, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdSkipped, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.AdError, (_event: any) => {\n this.eventCallback(Event.END_AD, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Muted, () => {\n this.eventCallback(Event.MUTE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Unmuted, () => {\n this.eventCallback(Event.UN_MUTE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.Error, (event: any) => {\n this.eventCallback(Event.ERROR, {\n code: event.code,\n message: event.name,\n legacyData: event.data,\n currentTime: this.currentTime,\n data: {\n additionalData: JSON.stringify(event.data),\n },\n });\n if (\n event.code === ErrorCode.BITMOVIN_PLAYER_LICENSING_ERROR.code ||\n event.code === ErrorCode.SETUP_MISSING_LICENSE_WHITELIST.code\n ) {\n this._onLicenseCallFailed.dispatch({});\n }\n this.ssaiService.sendAdEngagementErrorSample(event.code, event.name);\n });\n\n this.player.on(this.player.exports.PlayerEvent.PlaybackFinished, () => {\n this.eventCallback(Event.END, {currentTime: this.currentTime});\n });\n\n this.player.on(this.player.exports.PlayerEvent.DownloadFinished, (event: any) => {\n if (event.downloadType.indexOf('drm/license/') === 0) {\n this.drmPerformanceInfo = {\n drmType: event.downloadType.replace('drm/license/', ''),\n drmLoadTime: event.downloadTime * 1000,\n };\n }\n });\n\n this.player.on(this.player.exports.PlayerEvent.AudioChanged, (_event: any) => {\n this.eventCallback(Event.AUDIOTRACK_CHANGED, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SubtitleEnabled, (_event: any) => {\n this.eventCallback(Event.SUBTITLE_CHANGE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.SubtitleDisabled, (_event: any) => {\n this.eventCallback(Event.SUBTITLE_CHANGE, {\n currentTime: this.currentTime,\n });\n });\n\n this.player.on(this.player.exports.PlayerEvent.LicenseValidated, (event: any) => {\n if (event.data.analytics && event.data.analytics.key !== undefined) {\n this._onLicenseKeyReceived.dispatch({licenseKey: event.data.analytics.key});\n } else {\n this._onLicenseCallFailed.dispatch({});\n }\n });\n }\n\n private registerUnloadEventListeners() {\n let handleCollectorUnload = () => {\n if (!this.onBeforeUnLoadEvent) {\n this.onBeforeUnLoadEvent = true;\n // we use here the last tracked video time as we cannot be sure if the player is still working at this place\n const currentTime = this.lastTrackedCurrentTime;\n this.eventCallback(Event.UNLOAD, {currentTime});\n }\n this.release();\n };\n handleCollectorUnload = handleCollectorUnload.bind(true);\n\n this.player.on(this.player.exports.PlayerEvent.Destroy, handleCollectorUnload);\n this.windowEventTracker.addEventListener('beforeunload', handleCollectorUnload);\n this.windowEventTracker.addEventListener('unload', handleCollectorUnload);\n }\n\n private applySourceProperties(info: PlaybackInfo) {\n const source = this.player.getSource();\n if (isNullish(source)) {\n return;\n }\n\n info.videoTitle = source.title;\n info.mpdUrl = source.dash;\n info.m3u8Url = source.hls;\n\n const progSourceInfo = getSourceInfoFromBitmovinSourceConfig(source.progressive, this.player);\n info.progUrl = progSourceInfo.progUrl;\n if (this.player.getStreamType() === 'progressive') {\n info.videoBitrate = progSourceInfo.progBitrate;\n }\n }\n\n private applySubtitleProperties(info: PlaybackInfo) {\n let enabledSubtitle;\n if (this.player.subtitles) {\n enabledSubtitle = this.player.subtitles.list().find((s) => s.enabled === true);\n }\n\n info.subtitleEnabled = isNotNullish(enabledSubtitle);\n info.subtitleLanguage = isNotNullish(enabledSubtitle) ? enabledSubtitle.lang : null;\n }\n\n private applyPlaybackQualityProperties(info: PlaybackInfo) {\n const videoQuality = this.player.getPlaybackVideoData();\n if (isNotNullish(videoQuality)) {\n info.videoBitrate = videoQuality.bitrate;\n info.videoPlaybackHeight = videoQuality.height;\n info.videoPlaybackWidth = videoQuality.width;\n info.videoCodec = (videoQuality as any).codec;\n }\n\n const audioQuality = this.player.getPlaybackAudioData();\n if (isNotNullish(audioQuality)) {\n info.audioBitrate = audioQuality.bitrate;\n info.audioCodec = (audioQuality as any).codec;\n }\n }\n\n private applyCastingProperties(info: PlaybackInfo) {\n const isCasting = this.player.isCasting() || this.player.isAirplayActive() || false;\n info.isCasting = isCasting;\n if (!isCasting) {\n return;\n }\n\n // AirPlay\n if (this.player.isAirplayActive()) {\n info.castTech = CastTech.AirPlay;\n return;\n }\n\n // Casting Tech from RemoteControlConfig\n const remoteControlConfig = this.player.getConfig().remotecontrol;\n if (isNullish(remoteControlConfig)) {\n return;\n }\n\n switch (remoteControlConfig.type) {\n case 'googlecast':\n info.castTech = CastTech.GoogleCast;\n break;\n case 'websocket':\n info.castTech = CastTech.WebSocket;\n break;\n }\n }\n\n // with this check we ignore seek events which are smaller than the Threshold\n // mainly to ignore keyboard triggered seeks\n private allowSeeking(e: UserInteractionEvent): boolean {\n const seekEvent = e as SeekEvent;\n const seekDifference = Math.abs(seekEvent.position - seekEvent.seekTarget);\n return seekDifference > AnalyticsSettings.ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD;\n }\n\n static create(player: PlayerAPI, opts?: AnalyticsStateMachineOptions): Bitmovin8InternalAdapter {\n const speedMeter = new SpeedMeterAdapter(player, new DownloadSpeedMeter()).getDownloadSpeedMeter();\n const segmentTracker = new SegmentTrackerAdapter(player, new SegmentTracker()).getSegmentTracker();\n const httpRequestTrackingAdapter = new HttpRequestTrackingAdapter(player);\n const videoCompletionTracker = new VideoCompletionTracker();\n const sourceInfoFallbackService = new SourceInfoFallbackService();\n return new Bitmovin8InternalAdapter(\n player,\n speedMeter,\n segmentTracker,\n videoCompletionTracker,\n httpRequestTrackingAdapter,\n sourceInfoFallbackService,\n opts,\n );\n }\n}\n","import Timespan from '../types/Timespan';\nimport {isNullish} from '../utils/Utils';\n\nenum TimespanOverlappingType {\n None,\n Overlapping,\n FirstContainedInSecond,\n SecondContainedInFirst,\n}\n\nexport default class VideoCompletionTracker {\n private watched: Timespan[] = [];\n private videoDuration: number | null = null;\n\n reset(): void {\n this.watched = [];\n }\n\n /**\n * sets video Duration\n * @param videoDuration in sec\n */\n setVideoDuration(videoDuration: number): void {\n this.videoDuration = videoDuration * 1000;\n }\n\n /**\n * Adds the watched timespan to the tracker\n * @param watched watched timespan you want to add to the tracker\n * @returns how much time(video parts which have not been seen yet) was added to the tracker\n */\n addWatched(watched: Timespan): number {\n if (isNullish(this.videoDuration)) {\n throw new Error('no video duration set for completion tracker');\n }\n\n this.watched.push(watched);\n const overlappingTimespan = this.mergeWatched(this.watched);\n return (this.getDuration(watched) - overlappingTimespan) / this.videoDuration;\n }\n\n /**\n * returns the relative value of how much the user watch the content of the video\n */\n getCompletionPercentage(): number {\n if (isNullish(this.videoDuration)) {\n throw new Error('no video duration set for completion tracker');\n }\n\n let watched = 0;\n for (const w of this.watched) {\n watched += this.getDuration(w);\n }\n return watched / this.videoDuration;\n }\n\n /**\n * Recursive Method to merge All Watched Blocks\n * @param watched\n *\n * @returns how much timespan was overlapping while merging the watchBlocks\n */\n private mergeWatched(watched: Timespan[]): number {\n for (let i = 0; i < watched.length; i++) {\n const time1 = watched[i];\n for (let k = i + 1; k < watched.length; k++) {\n const time2 = watched[k];\n let overlappingTimespan = 0;\n const overlapType = this.getOverlappingType(time1, time2);\n\n if (overlapType === TimespanOverlappingType.Overlapping) {\n this.mergeAndReplace(time1, i, time2, k);\n overlappingTimespan = this.getOverlappingTimespan(time1, time2);\n } else if (overlapType === TimespanOverlappingType.FirstContainedInSecond) {\n this.watched.splice(i, 1);\n overlappingTimespan = this.getDuration(time1);\n } else if (overlapType === TimespanOverlappingType.SecondContainedInFirst) {\n this.watched.splice(k, 1);\n overlappingTimespan = this.getDuration(time2);\n }\n if (overlapType !== TimespanOverlappingType.None) {\n return overlappingTimespan + this.mergeWatched(this.watched);\n }\n }\n }\n return 0;\n }\n\n private getOverlappingType(first: Timespan, second: Timespan): TimespanOverlappingType {\n if (\n (this.isMomentInTimespan(first.end, second) && first.start < second.start) ||\n (this.isMomentInTimespan(first.start, second) && first.end > second.end)\n ) {\n return TimespanOverlappingType.Overlapping;\n } else if (this.isMomentInTimespan(first.start, second) && this.isMomentInTimespan(first.end, second)) {\n return TimespanOverlappingType.FirstContainedInSecond;\n } else if (this.isMomentInTimespan(second.start, first) && this.isMomentInTimespan(second.end, first)) {\n return TimespanOverlappingType.SecondContainedInFirst;\n }\n return TimespanOverlappingType.None;\n }\n\n private isMomentInTimespan(moment: number, timespan: Timespan): boolean {\n return moment >= timespan.start && moment < timespan.end;\n }\n\n private mergeAndReplace(first: Timespan, firstIndex: number, second: Timespan, secondIndex: number): void {\n const end = first.end > second.end ? first.end : second.end;\n const start = first.start < second.start ? first.start : second.start;\n const newWatchedTimespan: Timespan = {start, end};\n this.watched.splice(firstIndex, 1, newWatchedTimespan);\n this.watched.splice(secondIndex, 1);\n }\n\n private getOverlappingTimespan(first: Timespan, second: Timespan): number {\n const end = first.end < second.end ? first.end : second.end;\n const start = first.start >= second.start ? first.start : second.start;\n return end - start;\n }\n\n private getDuration(watched: Timespan): number {\n return Math.abs(watched.end - watched.start);\n }\n}\n","import {logger} from '../utils/Logger';\n\nimport {Feature} from './Feature';\nimport {FeatureConfig} from './FeatureConfig';\n\nexport class FeatureManager<TConfigContainer> {\n private features: Array<Feature<TConfigContainer, FeatureConfig>> = [];\n\n registerFeatures(features: Array<Feature<TConfigContainer, FeatureConfig>>) {\n this.features = features;\n }\n\n unregisterFeatures() {\n this.features.forEach((feature) => feature.disable());\n this.features = [];\n }\n\n resetFeatures() {\n this.features.forEach((feature) => feature.reset());\n }\n\n configureFeatures(authenticated: boolean, featureConfigs?: TConfigContainer) {\n this.features = this.features.filter((feature) => {\n const config = feature.configure(authenticated, featureConfigs);\n if (!authenticated || config?.enabled !== true) {\n logger.log(`Disabling feature ${feature.constructor.name} as it isn't enabled according to license callback.`);\n feature.disable();\n return false;\n }\n return true;\n });\n this.features.forEach((feature) => feature.enabled());\n }\n}\n","import {endsWith, isBlank} from '../utils/stringUtils';\nimport {isNullish} from '../utils/Utils';\n\nimport {MIMETypes} from './MIMETypes';\n\nexport enum StreamTypes {\n dash = 'dash',\n hls = 'hls',\n prog = 'progressive',\n}\n\nexport function getStreamTypesFromURL(url: string | undefined): StreamTypes | undefined {\n if (isNullish(url) || isBlank(url)) {\n return undefined;\n }\n\n const urlPath = url.split(/[?#]/)[0].toLowerCase();\n\n if (endsWith(urlPath, '.m3u8')) {\n return StreamTypes.hls;\n }\n if (endsWith(urlPath, '.mp4') || endsWith(urlPath, '.m4v') || endsWith(urlPath, '.m4a')) {\n return StreamTypes.prog;\n }\n if (endsWith(urlPath, '.webm')) {\n return StreamTypes.prog;\n }\n if (endsWith(urlPath, '.mpd')) {\n return StreamTypes.dash;\n }\n\n return undefined;\n}\n\nexport function getStreamTypeFromMIMEType(mimeType: string): StreamTypes | undefined {\n const MIME_TYPE_TO_STREAM_TYPE_MAP = {\n [MIMETypes.MP4]: StreamTypes.prog,\n [MIMETypes.WEBM]: StreamTypes.prog,\n [MIMETypes.HLS]: StreamTypes.hls,\n [MIMETypes.DASH]: StreamTypes.dash,\n };\n\n return MIME_TYPE_TO_STREAM_TYPE_MAP[mimeType];\n}\n","import type {AdBreak, AdBreakConfig, AdConfig, AdManifestLoadedEvent, AdTagConfig} from 'bitmovin-player';\n\nimport * as Utils from '../utils/Utils';\n\nexport class AdBreakSample {\n adPosition?: string;\n adOffset?: string;\n adScheduleTime?: number;\n adReplaceContentDuration?: number;\n adPreloadOffset?: number;\n adTagPath?: string;\n adTagServer?: string;\n adTagType?: string;\n adTagUrl?: string;\n adIsPersistent?: boolean;\n adIdPlayer?: string;\n manifestDownloadTime?: number;\n errorCode?: number;\n errorData?: string;\n errorMessage?: string;\n adFallbackIndex = 0;\n\n constructor(adConfig?: AdConfig, adManifestLoadedEvent?: AdManifestLoadedEvent) {\n if (adManifestLoadedEvent) {\n this.manifestDownloadTime = Utils.calculateTime(adManifestLoadedEvent.downloadTiming.downloadTime);\n }\n\n if (adConfig) {\n this.adReplaceContentDuration = Utils.calculateTimeWithUndefined(adConfig.replaceContentDuration);\n this.adFallbackIndex = ((adConfig as any).currentFallbackIndex || -1) + 1;\n }\n\n const adBreakConfig = adConfig as AdBreakConfig;\n if (adBreakConfig) {\n if (adBreakConfig.position === 'pre' || adBreakConfig.position === 'post') {\n this.adPosition = adBreakConfig.position;\n } else {\n this.adPosition = 'mid';\n this.adOffset = adBreakConfig.position;\n }\n\n this.adPreloadOffset = Utils.calculateTimeWithUndefined(adBreakConfig.preloadOffset);\n }\n\n const adTagConfig = adConfig as AdTagConfig;\n if (adTagConfig) {\n this.adIsPersistent = adTagConfig.persistent;\n let tag = adTagConfig.tag;\n if (\n this.adFallbackIndex > 0 &&\n adTagConfig.fallbackTags &&\n adTagConfig.fallbackTags.length >= this.adFallbackIndex\n ) {\n tag = adTagConfig.fallbackTags[this.adFallbackIndex - 1];\n }\n if (tag) {\n this.adTagType = tag.type;\n this.adTagUrl = tag.url;\n }\n if (this.adTagUrl) {\n const adTagDetails = Utils.getHostnameAndPathFromUrl(this.adTagUrl);\n this.adTagServer = adTagDetails.hostname;\n this.adTagPath = adTagDetails.path;\n }\n }\n\n const adBreak = adConfig as AdBreak;\n if (adBreak) {\n this.adScheduleTime = Utils.calculateTimeWithUndefined(adBreak.scheduleTime);\n this.adIdPlayer = adBreak.id;\n }\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {SEQUENCE_NUMBER_LIMIT} from '../utils/Settings';\n\nimport {Backend} from './Backend';\n\n/**\n * The `SequenceNumberBackend` is a decorator class that increments a samples sequence number and filters out samples\n * where the `sequenceNumber` exceeds a specified threshold.\n *\n * If a sample's `sequenceNumber` surpasses the threshold, it is not forwarded to the next backend.\n * Otherwise, the sample is passed along to the next backend for further processing.\n *\n * @implements {Backend}\n */\nexport class SequenceNumberBackend implements Backend {\n nextBackend: Backend;\n sequenceNumber = 0;\n\n constructor(underlying: Backend) {\n this.nextBackend = underlying;\n }\n\n sendRequest(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n this.updateSampleBeforeSending(sample);\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n if (this.isSequenceNumberAboveThreshold(sample)) {\n return;\n }\n this.nextBackend.sendAdRequest(sample);\n }\n\n private updateSampleBeforeSending(sample: Sample) {\n sample.sequenceNumber = this.sequenceNumber++;\n }\n\n private isSequenceNumberAboveThreshold(sample: Sample): boolean {\n return (sample.sequenceNumber ?? 0) > SEQUENCE_NUMBER_LIMIT;\n }\n}\n","import {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport type {AnalyticsConfig, AnalyticsDebugConfig} from '../types/AnalyticsConfig';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\n\nimport {Backend} from './Backend';\n\n/**\n * The `DebuggingBackend` is responsible for printing debugging information\n * before forwarding the requests to the specified underlying backend.\n *\n * This allows for inspection of specific fields in the sample data before it is sent.\n * The fields can be specified through the {@link AnalyticsDebugConfig#fields}.\n *\n * @implements {Backend}\n * */\nexport class DebuggingBackend implements Backend {\n private underlying: Backend;\n private debugFields?: string[];\n\n constructor(config: AnalyticsConfig, underlying: Backend) {\n this.underlying = underlying;\n if (config.debug && (config.debug as AnalyticsDebugConfig).fields) {\n this.debugFields = (config.debug as AnalyticsDebugConfig).fields;\n }\n }\n\n sendRequest(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendRequest(sample);\n }\n\n sendUnloadRequest(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendUnloadRequest(sample);\n }\n\n sendRequestSynchronous(sample: Sample) {\n this.printFields(sample);\n this.underlying.sendRequestSynchronous(sample);\n }\n\n sendAdRequest(sample: AdAnalyticsSample & AdBreakSample & AdSample) {\n this.underlying.sendAdRequest(sample);\n }\n\n private printFields(sample: Sample) {\n if (this.debugFields && this.debugFields.length) {\n const fields = {};\n this.debugFields.forEach((f) => (fields[f] = sample[f]));\n logger.table([fields]);\n }\n }\n}\n","import type {DownloadFinishedEvent, PlayerAPI, PlayerExports} from 'bitmovin-player';\n\nimport {EventDispatcher, Subscribable} from '../../../core/EventDispatcher';\nimport {OnDownloadFinishedEventObject} from '../../../features/httprequesttracking/OnDownloadFinishedEventObject';\nimport {calculateTimeWithUndefined, getCurrentTimestamp} from '../../../utils/Utils';\nimport {HttpRequestType} from '../bitmovin8PlayerTypes';\n\nexport class HttpRequestTrackingAdapter implements Subscribable<OnDownloadFinishedEventObject> {\n private eventDispatcher = new EventDispatcher<OnDownloadFinishedEventObject>();\n private playerExports: PlayerExports;\n\n constructor(player: PlayerAPI) {\n this.playerExports = player.exports;\n player.on(this.playerExports.PlayerEvent.DownloadFinished, (event) =>\n this.onDownloadFinished(event as DownloadFinishedEvent),\n );\n }\n\n subscribe(callback: (args: OnDownloadFinishedEventObject) => void): () => void {\n return this.eventDispatcher.subscribe(callback);\n }\n\n unsubscribe(callback: (args: OnDownloadFinishedEventObject) => void) {\n this.eventDispatcher.unsubscribe(callback);\n }\n\n private onDownloadFinished(event?: DownloadFinishedEvent) {\n this.eventDispatcher.dispatch({\n httpRequest: {\n downloadTime: calculateTimeWithUndefined(event?.downloadTime) ?? 0,\n httpStatus: event?.httpStatus ?? 0,\n success: event?.success ?? false,\n timestamp: getCurrentTimestamp(),\n url: event?.url,\n size: event?.size,\n timeToFirstByte: calculateTimeWithUndefined(event?.timeToFirstByte),\n type: this.mapHttpRequestType(event?.downloadType),\n },\n });\n }\n\n private mapHttpRequestType(downloadType?: string): HttpRequestType {\n // Map downloadType to the HttpRequestType values\n if (Object.values(HttpRequestType).includes(downloadType as HttpRequestType)) {\n return downloadType as HttpRequestType;\n }\n return HttpRequestType.UNKNOWN;\n }\n}\n","import type {HeartbeatListener} from '../core/HeartbeatService';\nimport {HeartbeatService} from '../core/HeartbeatService';\nimport {SSAI_RELATED_SAMPLE_MARKER} from '../core/ssai/ssaiUtils';\nimport {ErrorCode} from '../enums/ErrorCode';\nimport {Event, EventMap} from '../enums/Event';\nimport type {AnalyticsConfig} from '../types/AnalyticsConfig';\nimport type {AnalyticsStateMachineOptions} from '../types/AnalyticsStateMachineOptions';\nimport type {AnalyticsEventBase} from '../types/EventData';\nimport type {NoExtraProperties} from '../types/NoExtraProperties';\nimport {HeartbeatPayload, StateMachineCallbacks} from '../types/StateMachineCallbacks';\nimport {logger} from '../utils/Logger';\nimport * as Settings from '../utils/Settings';\nimport * as Utils from '../utils/Utils';\nimport {isNotNullish} from '../utils/Utils';\n\nconst REBUFFERING_HEARTBEAT_INTERVALS = [3000, 5000, 10000, 30000, 59700];\n\nexport abstract class AnalyticsStateMachine implements HeartbeatListener {\n protected stateMachine: StateMachine.StateMachine & {[key: string]: any};\n protected onEnterStateTimestamp = 0;\n\n protected readonly videoStartupTimeoutMs: number = Settings.ANALYTICS_VIDEOSTART_TIMEOUT;\n protected readonly rebufferTimeoutMs: number = Settings.ANALYTICS_REBUFFER_TIMEOUT;\n protected readonly playingHeartbeatService: HeartbeatService;\n\n private rebufferingHeartbeatIntervalHandle?: number;\n private currentRebufferingIntervalIndex = 0;\n private rebufferingTimeoutHandle?: number;\n private videoStartTimeout?: number;\n\n constructor(\n protected stateMachineCallbacks: StateMachineCallbacks,\n playingHeartbeatService: HeartbeatService,\n opts: AnalyticsStateMachineOptions,\n ) {\n this.stateMachine = this.createStateMachine(opts);\n this.playingHeartbeatService = playingHeartbeatService;\n }\n\n abstract createStateMachine(opts: AnalyticsStateMachineOptions): StateMachine.StateMachine;\n\n /**\n * Sends out sample because of SSAI interaction\n *\n * @param timestamp current timestamp\n * @param eventObject contains player information\n */\n abstract onSsaiPlaybackInteraction(timestamp: number, eventObject: AnalyticsEventBase): void;\n\n callEvent<StateMachineEvent extends keyof EventMap, StateMachineEventData extends EventMap[StateMachineEvent]>(\n event: StateMachineEvent,\n eventData: NoExtraProperties<EventMap[StateMachineEvent], StateMachineEventData>,\n eventTimestamp: number,\n ): void {\n const stateMachineEventMethod = this.stateMachine[event];\n\n if (stateMachineEventMethod == null) {\n // If the event (aka. the event method) is not defined in the JSM, we log a warning,\n // because it means that we are explicitly trying to call that JSM event from our code (probably adapter),\n // but it was not defined in the JSM at all. Either we are missing it or it should not be called at all!\n logger.warn(`StateMachine ignored event \"${event}\" call, because it was not defined`, eventData, eventTimestamp);\n return;\n }\n\n try {\n // By default, if you try to call an event method not allowed in the current state, the state machine will throw an exception.\n // see: https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n //\n // This JSM library behavior can be changed by providing \"a custom error handler\" in the `create()`\n // method of the state machine, and we do that in every state machine!\n //\n // But we still want to have here a try-catch block, in case of unexpected state machine code,\n // to avoid propagating the exception to the rest of the application (and breaking customer app).\n stateMachineEventMethod.call(this.stateMachine, eventTimestamp, eventData);\n } catch (e) {\n logger.error(\n `StateMachine ignored event \"${event}\" call, because it has thrown exception in the current state \"${this.currentState}\"`,\n eventData,\n eventTimestamp,\n e,\n );\n }\n }\n\n callManualSourceChangeEvent(analyticsConfig: AnalyticsConfig, playbackCurrentTimeInSeconds?: number) {\n this.callEvent(\n Event.MANUAL_SOURCE_CHANGE,\n {config: analyticsConfig, currentTime: playbackCurrentTimeInSeconds},\n Date.now(),\n );\n }\n\n get currentState(): string {\n return this.stateMachine.current;\n }\n\n resetIntervals() {\n this.clearVideoStartTimeout();\n this.clearRebufferingTimeoutHandle(true);\n this.clearRebufferingHeartbeatHandle();\n }\n\n //#region rebuffer timeout\n\n protected startRebufferingHeartbeatInterval(reset = true) {\n this.resetRebufferingHelpers(reset);\n\n this.startRebufferingTimeoutHandle();\n\n this.rebufferingHeartbeatIntervalHandle = window.setInterval(() => {\n const state = this.stateMachine.current.toLowerCase();\n if (state !== 'rebuffering') {\n this.resetRebufferingHelpers();\n return;\n }\n const timestamp = new Date().getTime();\n const stateDuration = timestamp - this.onEnterStateTimestamp;\n this.stateMachineCallbacks.heartbeat(stateDuration, state, {buffered: stateDuration});\n this.onEnterStateTimestamp = timestamp;\n this.currentRebufferingIntervalIndex = Math.min(\n this.currentRebufferingIntervalIndex + 1,\n REBUFFERING_HEARTBEAT_INTERVALS.length - 1,\n );\n this.startRebufferingHeartbeatInterval(false);\n }, REBUFFERING_HEARTBEAT_INTERVALS[this.currentRebufferingIntervalIndex]);\n }\n\n protected resetRebufferingHelpers(reset = true) {\n if (reset) {\n this.currentRebufferingIntervalIndex = 0;\n }\n this.clearRebufferingHeartbeatHandle();\n this.clearRebufferingTimeoutHandle(reset);\n }\n\n protected clearRebufferingHeartbeatHandle() {\n if (isNotNullish(this.rebufferingHeartbeatIntervalHandle)) {\n window.clearInterval(this.rebufferingHeartbeatIntervalHandle);\n this.rebufferingHeartbeatIntervalHandle = undefined;\n }\n }\n\n private startRebufferingTimeoutHandle() {\n if (this.currentRebufferingIntervalIndex > 0) {\n return;\n }\n this.rebufferingTimeoutHandle = window.setTimeout(() => {\n this.callEvent(\n Event.ERROR,\n {\n ...ErrorCode.BUFFERING_TIMEOUT_REACHED,\n data: {\n additionalData: `StateMachine timed out after ${this.rebufferTimeoutMs} ms of consecutive buffering.`,\n },\n },\n Utils.getCurrentTimestamp(),\n );\n this.stateMachineCallbacks.release();\n }, this.rebufferTimeoutMs);\n }\n\n protected clearRebufferingTimeoutHandle(reset: boolean) {\n if (reset && isNotNullish(this.rebufferingTimeoutHandle)) {\n window.clearTimeout(this.rebufferingTimeoutHandle);\n this.rebufferingTimeoutHandle = undefined;\n }\n }\n //#endregion\n\n //#region videoStartupFailed\n protected setVideoStartTimeout() {\n if (isNotNullish(this.videoStartTimeout)) {\n this.clearVideoStartTimeout();\n }\n this.videoStartTimeout = window.setTimeout(() => {\n this.callEvent(Event.VIDEOSTART_TIMEOUT, {}, Date.now());\n this.stateMachineCallbacks.release();\n }, this.videoStartupTimeoutMs);\n }\n\n protected clearVideoStartTimeout() {\n window.clearTimeout(this.videoStartTimeout);\n this.videoStartTimeout = undefined;\n }\n //#endregion\n\n onHeartbeat(eventObject: AnalyticsEventBase): void {\n this.sendPlayingSample(Date.now(), eventObject);\n }\n\n /**\n * Should be used in \"playing\" state only, and only by \"SSAI\" and \"Playing Heartbeat\" features,\n * otherwise it will log a warning and do nothing!\n *\n * Uses timestamp and eventObject.currentTime to reset time measurements and calls the\n * {@link StateMachineCallbacks.heartbeat} to send out a playing sample.\n *\n * We have chose to use {@link StateMachineCallbacks.heartbeat} callback here, because it was\n * the easiest and the fastest way to trigger 'playing' sample sending, without changing and\n * refactoring too much code, in future this code should be refactored with better naming.\n *\n * @param timestamp current timestamp\n * @param eventObject contains player information\n * @param triggeredBySsai boolean to mark the sample as SSAI triggered\n */\n protected sendPlayingSample(timestamp: number, eventObject: AnalyticsEventBase, triggeredBySsai = false) {\n const state = this.stateMachine.current.toLowerCase();\n if (state !== 'playing') {\n // our logic for \"SSAI\" and \"playing heartbeat\" is built on the assumption that we send only 'playing' samples,\n // but that \"if\" restriction is spread across the codebase, so we need to log a warning here, to see a potential\n // problems in our logic, if reported by from customer and report will contain these logs\n logger.warn(`Unexpected call of \"sendPlayingSample\" in AnalyticsStateMachine from \"${state}\" state`);\n return;\n }\n\n this.stateMachineCallbacks.setVideoTimeEndFromEvent(eventObject);\n\n const stateDuration = timestamp - this.onEnterStateTimestamp;\n const payload: HeartbeatPayload = {played: stateDuration};\n\n if (triggeredBySsai) {\n payload[SSAI_RELATED_SAMPLE_MARKER] = true;\n }\n\n this.stateMachineCallbacks.heartbeat(stateDuration, state, payload);\n\n this.onEnterStateTimestamp = timestamp;\n this.stateMachineCallbacks.setVideoTimeStartFromEvent(eventObject);\n }\n}\n","import {CollectorConfig} from '../../types/AnalyticsConfig';\nimport {post} from '../../utils/Http';\nimport {ANALYTICS_BACKEND_BASE_URL} from '../../utils/Settings';\nimport {isNotNullish, joinUrls} from '../../utils/Utils';\nimport {HttpRequest} from '../httprequesttracking/HttpRequest';\n\nimport {ErrorData} from './ErrorData';\nimport {ErrorDetail} from './ErrorDetail';\n\nexport class ErrorDetailBackend {\n get queue(): ReadonlyArray<ErrorDetail> {\n return this._queue;\n }\n\n get enabled(): boolean {\n return this._enabled;\n }\n\n set enabled(value: boolean) {\n this._enabled = value;\n }\n\n static copyErrorDetailTruncateStringsAndUrls(\n errorDetail: ErrorDetail,\n maxStringLength: number,\n maxUrlLength: number,\n ): ErrorDetail {\n return {\n ...errorDetail,\n message: errorDetail.message?.substr(0, maxStringLength),\n data: this.copyErrorDataTruncateStrings(errorDetail.data, maxStringLength),\n httpRequests: errorDetail.httpRequests?.map((request) => this.copyHttpRequestTruncateUrls(request, maxUrlLength)),\n };\n }\n\n static copyHttpRequestTruncateUrls(httpRequest: HttpRequest, maxLength: number): HttpRequest {\n return {\n ...httpRequest,\n url: httpRequest.url?.substr(0, maxLength),\n lastRedirectLocation: httpRequest.lastRedirectLocation?.substr(0, maxLength),\n };\n }\n\n static copyErrorDataTruncateStrings(errorData: ErrorData, maxStringLength: number): ErrorData {\n return {\n ...errorData,\n exceptionMessage: errorData.exceptionMessage?.substr(0, maxStringLength),\n additionalData: errorData.additionalData?.substr(0, maxStringLength),\n };\n }\n\n static copyErrorDetailTruncateHttpRequests(errorDetail: ErrorDetail, maxRequests: number): ErrorDetail {\n return {\n ...errorDetail,\n httpRequests: errorDetail.httpRequests?.slice(-maxRequests),\n };\n }\n\n // We use these as upper limits to avoid clients bombing us with data, actual truncation to documented limits is\n // happening in ingress\n private static MAX_URL_LENGTH = 450;\n private static MAX_STRING_LENGTH = 400;\n\n private readonly backendUrl: string;\n private readonly _queue: ErrorDetail[] = [];\n private _enabled = false;\n\n constructor(collectorConfig: CollectorConfig | undefined) {\n this.backendUrl = joinUrls(collectorConfig?.backendUrl ?? ANALYTICS_BACKEND_BASE_URL, '/analytics/error');\n }\n\n limitHttpRequestsOfQueuedErrorDetails(max: number) {\n this._queue.forEach((value, index) => {\n this._queue[index] = ErrorDetailBackend.copyErrorDetailTruncateHttpRequests(value, max);\n });\n }\n\n send(errorDetail: ErrorDetail) {\n const errorDetailCopy = ErrorDetailBackend.copyErrorDetailTruncateStringsAndUrls(\n errorDetail,\n ErrorDetailBackend.MAX_STRING_LENGTH,\n ErrorDetailBackend.MAX_URL_LENGTH,\n );\n if (this.enabled) {\n post(this.backendUrl, errorDetailCopy, () => undefined);\n } else {\n this._queue.push(errorDetailCopy);\n }\n }\n\n flush() {\n const copy = [...this._queue];\n let element = copy.shift();\n while (isNotNullish(element)) {\n this.removeFromQueue(element);\n this.send(element);\n element = copy.shift();\n }\n }\n\n clear() {\n this._queue.splice(0, this._queue.length);\n }\n\n private removeFromQueue(element: ErrorDetail) {\n const index = this._queue.findIndex((value) => value === element);\n if (index >= 0) {\n this._queue.splice(index, 1);\n }\n }\n}\n","/**\n * This class is used to limit error reporting for identical consecutive error codes per session.\n *\n * Repeated consecutive errors of the same code are limited to {@link IdenticalErrorReportingLimiter.MAX_IDENTICAL_ERROR_REPORTING}.\n */\nexport class IdenticalErrorReportingLimiter {\n /** The maximum number of times the same error code can be reported consecutively. */\n private static MAX_IDENTICAL_ERROR_REPORTING = 5;\n\n private _lastErrorCode: number | undefined;\n private _currentErrorCount = 0;\n\n /**\n * Determines whether an error with the given errorCode should be reported,\n * based on the limit of identical consecutive error reports.\n *\n * @param errorCode - The error code for which we are checking the reporting conditions.\n * @returns {boolean} - Returns true if the error can be reported, false if it exceeds the limits.\n */\n shouldReportError(errorCode: number): boolean {\n if (errorCode === this._lastErrorCode) {\n this._currentErrorCount++;\n return this._currentErrorCount <= IdenticalErrorReportingLimiter.MAX_IDENTICAL_ERROR_REPORTING;\n }\n\n this._lastErrorCode = errorCode;\n this._currentErrorCount = 1;\n return true;\n }\n\n reset() {\n this._lastErrorCode = undefined;\n this._currentErrorCount = 0;\n }\n}\n","import {Subscribable} from '../../core/EventDispatcher';\nimport {logger} from '../../utils/Logger';\nimport {Queue} from '../../utils/Queue';\n\nimport {HttpRequest} from './HttpRequest';\nimport {OnDownloadFinishedEventObject} from './OnDownloadFinishedEventObject';\n\nexport class HttpRequestTracking {\n private static DEFAULT_MAX_REQUESTS = 10;\n private _maxRequests: number = HttpRequestTracking.DEFAULT_MAX_REQUESTS;\n private _httpRequestQueue = new Queue<HttpRequest>();\n\n get maxRequests(): number {\n return this._maxRequests;\n }\n\n get httpRequests(): ReadonlyArray<HttpRequest> {\n return this._httpRequestQueue.items;\n }\n\n constructor(private subscribables: Array<Subscribable<OnDownloadFinishedEventObject>>) {\n subscribables.forEach((subscribable) => subscribable.subscribe(this.onDownloadFinishedHandler));\n }\n\n configure(maxRequests: number) {\n this._maxRequests = maxRequests;\n this._httpRequestQueue.limit(maxRequests);\n }\n\n disable() {\n this.subscribables.forEach((subscribable) => subscribable.unsubscribe(this.onDownloadFinishedHandler));\n this._httpRequestQueue.clear();\n }\n\n reset() {\n this._httpRequestQueue.clear();\n }\n\n private onDownloadFinishedHandler = (event: OnDownloadFinishedEventObject) => {\n try {\n this.addRequest(event.httpRequest);\n } catch (error) {\n logger.error(`HttpRequestTracking.onDownloadFinished: Error in handler`, error);\n }\n };\n\n private addRequest(httpRequest: HttpRequest) {\n this._httpRequestQueue.offer(httpRequest);\n this._httpRequestQueue.limit(this._maxRequests);\n }\n}\n","import type {SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\nimport {customDataValuesKeys} from '../../types/CustomDataValues';\nimport type {AdSample, Sample} from '../../types/Sample';\nimport {isNotNullish, isNullish} from '../../utils/Utils';\n\nimport type {\n InternalSsaiMetadata,\n SsaiEngagementErrorData,\n SsaiEngagementQuartileData,\n SsaiEngagementStartedData,\n} from './ssaiEngagementInteractionData';\n\n/**\n * Ssai marker property for {@link Sample} to indicate that this is \"ssai related sample\" and can cause the spike\n * on ingress side. It will be picked up in `AnalyticsCall` and used to send that \"ssai related sample\" as request\n * with ssai redirection. @see {@link ROUTING_URL_PARAM}\n *\n * What is \"ssai related sample\" ?\n * - \"last sample\" that was triggered to be sent, because of coming SSAI interaction, the SSAI ad break start (WITHOUT `sample.ad = 2`),\n * because it causes also the spike as all viewers are received same SSAI at the same time.\n * - all following samples, triggered by SSAI interaction while SSAI ad break is running (now WITH `sample.ad = 2`)\n *\n * We don't we need it with {@link AdSample} too?\n * Because all \"ssai related ad samples\" are triggered only during ssai ad break, so all have already\n * {@link AdSample#adType} property set and we can relay on that in `AnalyticsCall` to send them with ssai redirection.\n */\nexport const SSAI_RELATED_SAMPLE_MARKER = 'triggeredBySsai';\n\nexport function isSsaiRelatedSample(sample: AdSample | Sample): boolean {\n if (sample[SSAI_RELATED_SAMPLE_MARKER]) {\n delete sample[SSAI_RELATED_SAMPLE_MARKER]; // clean up the marker property that should not be present on the sample property\n return true;\n } else if ((sample as AdSample).adType === 2) {\n return true;\n }\n\n return false;\n}\n\n/**\n * Due to ssai being spiky by design, we should mark all analytics requests (with samples / ad samples)\n * that are ssai related, with a specific URL parameter. The load balancer can then route traffic according to the URL\n * parameter to a different ingress instance, which gives us more flexibility when ssai spikes are coming in.\n */\nexport const ROUTING_URL_PARAM = 'routingParam';\nexport const ROUTING_URL_PARAM_VALUE_SSAI = 'ssai';\n\nexport function appendSsaiRoutingParam(url: string): string {\n return `${url}?${ROUTING_URL_PARAM}=${ROUTING_URL_PARAM_VALUE_SSAI}`;\n}\n\nfunction createAdSampleFromSample(sample: Sample): AdSample {\n return {\n audioBitrate: sample?.audioBitrate,\n analyticsVersion: sample?.analyticsVersion,\n adPlaybackHeight: sample?.videoPlaybackHeight,\n adPlaybackWidth: sample?.videoPlaybackWidth,\n cdnProvider: sample?.cdnProvider,\n customData1: sample?.customData1,\n customData2: sample?.customData2,\n customData3: sample?.customData3,\n customData4: sample?.customData4,\n customData5: sample?.customData5,\n customData6: sample?.customData6,\n customData7: sample?.customData7,\n customData8: sample?.customData8,\n customData9: sample?.customData9,\n customData10: sample?.customData10,\n customData11: sample?.customData11,\n customData12: sample?.customData12,\n customData13: sample?.customData13,\n customData14: sample?.customData14,\n customData15: sample?.customData15,\n customData16: sample?.customData16,\n customData17: sample?.customData17,\n customData18: sample?.customData18,\n customData19: sample?.customData19,\n customData20: sample?.customData20,\n customData21: sample?.customData21,\n customData22: sample?.customData22,\n customData23: sample?.customData23,\n customData24: sample?.customData24,\n customData25: sample?.customData25,\n customData26: sample?.customData26,\n customData27: sample?.customData27,\n customData28: sample?.customData28,\n customData29: sample?.customData29,\n customData30: sample?.customData30,\n customData31: sample?.customData31,\n customData32: sample?.customData32,\n customData33: sample?.customData33,\n customData34: sample?.customData34,\n customData35: sample?.customData35,\n customData36: sample?.customData36,\n customData37: sample?.customData37,\n customData38: sample?.customData38,\n customData39: sample?.customData39,\n customData40: sample?.customData40,\n customData41: sample?.customData41,\n customData42: sample?.customData42,\n customData43: sample?.customData43,\n customData44: sample?.customData44,\n customData45: sample?.customData45,\n customData46: sample?.customData46,\n customData47: sample?.customData47,\n customData48: sample?.customData48,\n customData49: sample?.customData49,\n customData50: sample?.customData50,\n customUserId: sample?.customUserId,\n domain: sample?.domain,\n experimentName: sample?.experimentName,\n key: sample?.key,\n language: sample?.language,\n path: sample?.path,\n platform: sample?.platform,\n player: sample?.player,\n playerKey: sample?.playerKey,\n playerTech: sample?.playerTech,\n size: sample?.size,\n screenHeight: sample?.screenHeight,\n screenWidth: sample?.screenWidth,\n streamFormat: sample?.streamFormat,\n userAgent: sample?.userAgent,\n userId: sample?.userId,\n version: sample?.version,\n videoBitrate: sample?.videoBitrate,\n videoId: sample?.videoId,\n videoImpressionId: sample?.impressionId,\n videoTitle: sample?.videoTitle,\n videoWindowHeight: sample?.videoWindowHeight,\n videoWindowWidth: sample?.videoWindowWidth,\n };\n}\n\nexport function createErrorAdSample(\n playbackSample: Sample,\n ssaiEngagementErrorData: SsaiEngagementErrorData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementErrorData.currentAdImpressionId,\n adIndex: ssaiEngagementErrorData.adIndex,\n currentAdMetadata: ssaiEngagementErrorData.currentAdMetadata,\n quartile: undefined,\n quartileMetadata: undefined,\n errorCode: ssaiEngagementErrorData.errorCode,\n errorMessage: ssaiEngagementErrorData.errorMessage,\n timeSinceAdStartedInMs: ssaiEngagementErrorData.timeSinceAdStartedInMs,\n });\n}\n\nexport function createStartedAdSample(\n playbackSample: Sample,\n ssaiEngagementStartedData: SsaiEngagementStartedData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementStartedData.currentAdImpressionId,\n adIndex: ssaiEngagementStartedData.adIndex,\n currentAdMetadata: ssaiEngagementStartedData.currentAdMetadata,\n quartile: 'started',\n quartileMetadata: undefined,\n errorCode: undefined,\n errorMessage: undefined,\n timeSinceAdStartedInMs: undefined,\n });\n}\n\nexport function createQuartileAdSample(\n playbackSample: Sample,\n ssaiEngagementQuartileData: SsaiEngagementQuartileData,\n): AdSample {\n return buildAdSample({\n playbackSample,\n currentAdImpressionId: ssaiEngagementQuartileData.currentAdImpressionId,\n adIndex: ssaiEngagementQuartileData.adIndex,\n currentAdMetadata: ssaiEngagementQuartileData.currentAdMetadata,\n quartile: ssaiEngagementQuartileData.quartile,\n quartileMetadata: ssaiEngagementQuartileData.quartileMetadata,\n timeSinceAdStartedInMs: ssaiEngagementQuartileData.timeSinceAdStartedInMs,\n errorCode: undefined,\n errorMessage: undefined,\n });\n}\n\nfunction buildAdSample({\n playbackSample,\n currentAdImpressionId,\n adIndex,\n currentAdMetadata,\n quartile,\n quartileMetadata,\n errorCode,\n errorMessage,\n timeSinceAdStartedInMs,\n}: {\n adIndex: number;\n currentAdImpressionId: string;\n currentAdMetadata: InternalSsaiMetadata;\n errorCode: number | undefined;\n errorMessage: string | undefined;\n playbackSample: Sample;\n quartile: 'started' | SsaiAdQuartile | undefined;\n quartileMetadata: SsaiAdQuartileMetadata | undefined;\n timeSinceAdStartedInMs: number | undefined;\n}): AdSample {\n const adEngagementSample: AdSample = {\n ...createAdSampleFromSample(playbackSample),\n adId: currentAdMetadata?.adId,\n adImpressionId: currentAdImpressionId,\n adIndex: adIndex,\n adPosition: currentAdMetadata?.adPosition,\n adSystem: currentAdMetadata?.adSystem,\n adType: 2,\n errorCode: errorCode,\n errorMessage: errorMessage,\n time: Date.now(),\n timeSinceAdStartedInMs: timeSinceAdStartedInMs,\n };\n\n // set quartile data\n switch (quartile) {\n case 'started':\n adEngagementSample.started = 1;\n break;\n case 'first':\n adEngagementSample.quartile1 = 1;\n adEngagementSample.quartile1FailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'midpoint':\n adEngagementSample.midpoint = 1;\n adEngagementSample.midpointFailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'third':\n adEngagementSample.quartile3 = 1;\n adEngagementSample.quartile3FailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n case 'completed':\n adEngagementSample.completed = 1;\n adEngagementSample.completedFailedBeaconUrl = quartileMetadata?.failedBeaconUrl;\n break;\n }\n\n // set ssai customData\n const customData = currentAdMetadata?.customData;\n if (isNotNullish(customData)) {\n customDataValuesKeys.forEach((key) => {\n if (customData[key]) {\n adEngagementSample[key] = customData[key];\n }\n });\n }\n\n return adEngagementSample;\n}\n\n/**\n * Returns the current timestamp in milliseconds using the `performance.now()` method if available\n * to ensure monotonic timestamps; otherwise, it falls back to using `Date.now()`.\n *\n * Date.now() is dependent on the system clock and not monotonic, it may have been impacted by system\n * and user clock adjustments. The performance.now() method is relative to the timeOrigin property\n * which is a monotonic clock: its current time never decreases and isn't subject to adjustments.\n */\nexport function getCurrentMonotonicTimestampInMs(): number {\n if (isNullish(window.performance?.now) || typeof window.performance.now !== 'function') {\n return Date.now();\n }\n\n // floor to return integer value (not double as performance.now() returns)\n return Math.floor(performance.now());\n}\n\nexport function getMonotonicTimestampInMsSince(timestampInMs: number | undefined): number | undefined {\n if (isNullish(timestampInMs)) {\n return undefined;\n }\n\n return getCurrentMonotonicTimestampInMs() - timestampInMs;\n}\n","import {\n StateMachineErrorCallback,\n Error as StateMachineErrorCode,\n StateMachineEventDef,\n} from 'javascript-state-machine';\n\nimport {logger, padRight} from '../utils/Logger';\nimport {isNotNullish, isNullish} from '../utils/Utils';\n\n/**\n * @deprecated use {@link whileIn} instead, to switch mindset and think about allowed events in the current state\n * instead of thinking of current event and its allowed states. Because as analytics we focus mostly on reporting\n * states or states changes.\n */\nexport const on = (event: string): {stayIn: (state: string) => StateMachineEventDef} => ({\n stayIn: (state: string) => ({name: event, from: state, to: state}),\n});\n\ntype EventsToStateMachineEventDefFn = (...events: string[]) => StateMachineEventDef[];\ntype WhileInReturnType = {\n /**\n * Create {@link StateMachineEventDef} from event(s) to be used in the state machine definition, but ONLY to indicate\n * that we want to only pass event(s) over, to avoid a log message of ignored event in the current state from\n * the state machine.\n *\n * @remarks\n *\n * If we decide in the future to ignore {@link StateMachineErrorCode.INVALID_TRANSITION} logs created in\n * {@link customStateMachineErrorCallback}, this method and JSM event definitions created with could be removed\n * from source code. Until then, we use it to make code more readable.\n */\n passOver: EventsToStateMachineEventDefFn;\n\n /**\n * Same as {@link passOver}, but used in rare cases, when it indicates that we expect the event(s) to occur\n * in the current state, aka. we want to trigger the state machine event callbacks for these event(s),\n * even if we stay in the same state.\n *\n * @remarks\n *\n * If we don't expect the event while staying in the current state, we don't expect state machine event callbacks\n * to run, we should use {@link passOver} instead!\n */\n runEventCallbacksFor: EventsToStateMachineEventDefFn;\n};\n\n/**\n * This utility is here to help us write more readable code and let us define allowed/expected events in the current state.\n *\n * ### Example:\n *\n * Instead of writing:\n *\n * ```typescript\n * {name: Event.PAUSE, from: State.END, to: State.END},\n * {name: Event.SEEK, from: State.END, to: State.END},\n * {name: Event.SEEKED, from: State.END, to: State.END},\n * {name: Event.TIMECHANGED, from: State.END, to: State.END},\n * ```\n *\n * we can write:\n *\n * ```typescript\n * ...whileIn(State.END).passOver(Event.PAUSE, Event.SEEK, Event.SEEKED, Event.TIMECHANGED),\n * // OR when we expect and react on that event occurrence:\n * ...whileIn(State.END).runEventCallbacksFor(Event.PAUSE, Event.SEEK, Event.SEEKED, Event.TIMECHANGED),\n * ```\n *\n * @see customStateMachineErrorCallback\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n */\nexport const whileIn = (state: string): WhileInReturnType => {\n const stateMachineEventDefBuilderFn = (...events: string[]) =>\n events.map((event) => ({name: event, from: state, to: state}));\n return {runEventCallbacksFor: stateMachineEventDefBuilderFn, passOver: stateMachineEventDefBuilderFn};\n};\n\n/**\n * By default, if you try to call an event method not allowed in the current state,\n * the state machine will throw an exception (not allow it).\n *\n * This JSM library behavior can be changed by providing \"a custom error handler\" in the `create()`\n * method of the state machine, and we do that in every state machine!\n *\n * This way we make code more resilient to errors, because we do not throw errors from JSM event methods,\n * but instead we handle them here and just log them with {@link logger}.\n *\n * @see https://github.com/jakesgordon/javascript-state-machine/blob/2.4.0/README.md#handling-failures\n */\nexport const customStateMachineErrorCallback: StateMachineErrorCallback = (\n eventName,\n from,\n to,\n args,\n errorCode,\n errorMessage,\n _ex,\n) => {\n const loggerMessage = `StateMachine ignored event \"${eventName}\", ${errorMessage}`;\n const loggerMessageData = {\n eventName,\n from,\n to,\n args: isNotNullish(args) ? JSON.stringify(args) : undefined,\n errorCode,\n errorMessage,\n };\n\n // if caller tried to fire an event that was inappropriate in the current state\n if (errorCode === StateMachineErrorCode.INVALID_TRANSITION) {\n // The event itself is defined in JSM (in some other StateMachineEventDef). However, it is just not considered to\n // be appropriate in the current state.\n //\n // We should log it as a simple log. It is not an error nor a warning,\n // - because JSM will just stay in the same JSM state (and that can be considered as expected behavior)\n // - BUT it will NOT trigger JSM event callbacks like `onafterEVENT`, on `onbeforeEVENT`!\n logger.log(loggerMessage, loggerMessageData);\n return;\n }\n\n logger.error(loggerMessage, loggerMessageData);\n};\n\n/**\n * Log warning messages with {@link logger} about missing StateMachine callback,\n * if the state is not nullish and does not match any of the ignored states.\n */\nexport const logMissingCallbackWarning = (state: string | undefined, ignoreStates: string[] = []) => {\n if (isNullish(state)) {\n return;\n }\n\n const shouldReportMissingCallback = isNullish(ignoreStates.find((ignoredState) => state === ignoredState));\n if (shouldReportMissingCallback) {\n logger.warn('Could not find StateMachine callback function for ' + state);\n }\n};\n\n/** Log message with {@link logger} about StateMachine ENTER/LEAVE transition */\nexport const logStateMachineTransition = (\n transition: 'ENTER' | 'LEAVE',\n event: string | undefined,\n from: string | undefined,\n to: string | undefined,\n) => {\n if (transition === 'ENTER') {\n logger.log(`[ENTER] ${padRight(to, 20)} EVENT: ${padRight(event, 20)} from ${padRight(from, 20)}`);\n } else {\n logger.log(`[LEAVE] ${padRight(from, 20)} EVENT: ${padRight(event, 20)} to ${padRight(to, 20)}`);\n }\n};\n\n/**\n * Return all values/states of the given state string enum.\n *\n * @param stateStringEnumObj\n *\n * @remarks\n *\n * We cannot directly check at if an object is a TypeScript string enum, because enums are erased at compile time and\n * become plain objects in JavaScript. However, you can heuristically check if an object looks like a string enum\n * by verifying that all its values are strings. This checks if all values of the object are strings, which is typical\n * for a string enum. However, this is not a foolproof check, just a heuristic.\n */\nexport function getAllStates<T extends {[key: string]: string}>(stateStringEnumObj: T): Array<T[keyof T]> {\n return Object.values(stateStringEnumObj) as Array<T[keyof T]>;\n}\n\nexport function getAllStatesBut<T extends {[key: string]: string}>(\n excludedStates: Array<T[keyof T]>,\n stateEnumObj: T,\n): Array<T[keyof T]> {\n return getAllStates(stateEnumObj).filter((s) => excludedStates.indexOf(s) < 0);\n}\n","import type {AnalyticsConfig, CollectorConfig} from '../types/AnalyticsConfig';\nimport type {Sample} from '../types/Sample';\n\nimport {logger} from './Logger';\nimport {isBlank, isValidString} from './stringUtils';\nimport * as Utils from './Utils';\nimport {isNotNullish, isNullish} from './Utils';\n\n/**\n * Sanitize {@link AnalyticsConfig} to not be null/undefined\n *\n * Why we return the same config (same reference) passed to function as an argument?\n * Because in the past, we made a mistake and forget to prevent changing `AnalyticsConfig` vie kept reference\n * from outside. Now our customers are using this bug/feature, and we need to keep it for backward compatibility.\n * This should be fixed and changed in the future major release as part of `Collector API v3` changes.\n *\n * @returns A new empty config `{}`, if it was `null/undefined`, otherwise the same config (same reference).\n *\n */\nexport function sanitizeAnalyticsConfig(config: AnalyticsConfig | null | undefined): AnalyticsConfig {\n if (isNullish(config)) {\n return {};\n }\n\n if (!Utils.isBoolean(config.isLive)) {\n config.isLive = undefined;\n }\n\n return config;\n}\n\n/**\n * Log error with {@link logger}, if the new configuration is missing `title` property, but old configuration had one.\n */\nexport function guardConfigChangeAgainstMissingTitle(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig) {\n if (isNullish(oldConfig) || isNullish(newConfig)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (oldConfig.title && isBlank(newConfig.title)) {\n logger.error('The new analytics configuration does not contain the field `title`');\n }\n}\n\n/**\n * Log error with {@link logger}, if the new configuration is missing `isLive` property, but old configuration had one.\n */\nexport function guardConfigChangeAgainstMissingIsLive(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig) {\n if (isNullish(oldConfig) || isNullish(newConfig)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (oldConfig.isLive && isNullish(newConfig.isLive)) {\n logger.error(\n 'The new analytics configuration does not contain the field `isLive`. It will default to `false` which might be unintended? Once stream playback information is available the type will be populated.',\n );\n }\n}\n\n/**\n * Log warning with {@link logger}, if both `customUserId` and `userId` are set in the configuration.\n */\nexport function guardAgainstDuplicatedUserId(config: AnalyticsConfig) {\n if (isNullish(config)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return;\n }\n\n if (isNotNullish(config.customUserId) && isNotNullish(config.userId)) {\n logger.warn(\n 'Configuration Warning: \\n' +\n 'CustomUserId and UserId are set in the config \\n' +\n 'Value of UserId will be used in sample \\n' +\n 'Please only use one configuration field to set your userId',\n );\n }\n}\n\nexport function getDeviceInformationFromAnalyticsConfig(\n config: AnalyticsConfig,\n): Sample['deviceInformation'] | undefined {\n if (isNullish(config)) {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return undefined;\n }\n\n const deviceInformation: Sample['deviceInformation'] = {};\n\n if (isValidString(config.deviceType) && !isBlank(config.deviceType)) {\n // we are using `deviceInformation.model` field to pass `config.deviceType`, because of ingress\n // and how deviceInformation processing is implemented there.\n deviceInformation.model = config.deviceType;\n }\n\n if (isValidString(config.deviceClass) && !isBlank(config.deviceClass)) {\n deviceInformation.deviceClass = config.deviceClass;\n }\n\n if (Object.keys(deviceInformation).length === 0) {\n return undefined;\n }\n\n return deviceInformation;\n}\n\n/**\n * Get {@link CollectorConfig} `origin` field (if any), otherwise return sanitized hostname.\n */\nexport function getDomainFromAnalyticsConfig(config: AnalyticsConfig): string {\n // handle undefined values even when argument type does not specify them\n // (defensive approach, because of old code from past and step by step refactorings)\n return config?.config?.origin ?? Utils.sanitizePath(window.location.hostname);\n}\n\nfunction removeSourceRelatedFields(config: AnalyticsConfig): AnalyticsConfig {\n const sourceSpecificProperties = ['cdnProvider', 'videoId', 'title', 'isLive', 'experimentName'];\n const customDataFieldsRegex = /customData\\d{1,2}$/g;\n\n for (const key in config) {\n if (isNotNullish(key.match(customDataFieldsRegex)) || sourceSpecificProperties.includes(key)) {\n delete config[key];\n }\n }\n\n return config;\n}\n\nfunction mergeCollectorConfig(\n oldCollectorConfig: CollectorConfig | undefined,\n newCollectorConfig: CollectorConfig | undefined,\n): CollectorConfig {\n if (isNotNullish(newCollectorConfig)) {\n // merging new config should enable the collector by default (unless explicitly disabled in the new config)\n return {...oldCollectorConfig, enabled: true, ...newCollectorConfig};\n }\n return oldCollectorConfig ?? {};\n}\n\nexport function mergeAnalyticsConfig(oldConfig: AnalyticsConfig, newConfig: AnalyticsConfig): AnalyticsConfig {\n const oldConfigWithoutSourceRelatedFields = removeSourceRelatedFields(oldConfig);\n const mergedCollectorConfig = mergeCollectorConfig(oldConfig.config, newConfig.config);\n\n return {\n ...oldConfigWithoutSourceRelatedFields,\n ...newConfig,\n config: mergedCollectorConfig,\n };\n}\n","import {isBlank, isValidString} from './stringUtils';\n\n// Declaration merging to extend the Window interface with WebOS API\n// see: https://webostv.developer.lge.com/develop/references/webostvjs-webos\ndeclare global {\n interface Window {\n /**\n * @deprecated In webOS TV 4.x or lower, only PalmSystem is supported, and in webOS TV 5.0 or higher,\n * both PalmSystem and webOSSystem are supported. Although PalmSystem is still supported for backward compatibility,\n * future support is not guaranteed so it is strongly recommended that you use webOSSystem in webOS TV 5.0 or higher.\n *\n * @see https://webostv.developer.lge.com/develop/guides/app-lifecycle-management\n */\n PalmSystem?: {\n deviceInfo?: string;\n };\n\n /**\n * Represents the current system interface that should be used on webOS TV 5.0 or higher.\n *\n * @see https://webostv.developer.lge.com/develop/references/webostvjs-webos\n */\n webOSSystem?: {\n /**\n * @see https://webostv.developer.lge.com/develop/references/webostvjs-webos#deviceinfo\n */\n deviceInfo?: string;\n };\n }\n}\n\ntype WebOSDeviceInfo = {modelName: string};\n\nexport function getWebOSTVModelName(): string | undefined {\n try {\n const info: WebOSDeviceInfo | undefined = window.webOSSystem?.deviceInfo\n ? JSON.parse(window.webOSSystem.deviceInfo)\n : window.PalmSystem?.deviceInfo && JSON.parse(window.PalmSystem.deviceInfo);\n if (isValidString(info?.modelName) && !isBlank(info?.modelName)) {\n return info.modelName;\n }\n return undefined;\n } catch {\n return undefined;\n }\n}\n\nexport function hasWindowWebOSApi(): boolean {\n return window.webOSSystem !== undefined || window.PalmSystem !== undefined;\n}\n","export enum PlayerSize {\n Fullscreen = 'FULLSCREEN',\n Window = 'WINDOW',\n}\n","import type {PlayerAPI} from 'bitmovin-player';\n\nimport {SegmentTracker} from '../../../core/SegmentTracker';\nimport {SegmentInfo} from '../../../types/SegmentInfo';\nimport * as Utils from '../../../utils/Utils';\n\ninterface DownloadFinishedEvent {\n attempt?: number;\n downloadType?: string;\n httpStatus: number;\n mimeType?: string;\n success: boolean;\n timestamp: number;\n type: string;\n url: string;\n}\n\ninterface SegmentPlaybackEvent {\n duration?: number;\n mediaInfo?: any;\n mimeType?: string;\n playbackTime?: number;\n representationId?: string;\n timestamp?: number;\n type?: string;\n uid?: string;\n url?: string;\n}\n\nexport class SegmentTrackerAdapter {\n private segmentTracker: SegmentTracker;\n\n constructor(player: PlayerAPI, segmentTracker: SegmentTracker) {\n this.segmentTracker = segmentTracker;\n\n player.on(player.exports.PlayerEvent.DownloadFinished, (event) => this.handleOnDownloadFinishEvent(event));\n player.on(player.exports.PlayerEvent.SegmentPlayback, (event) => this.handleSegmentPlaybackEvent(event));\n }\n\n getSegmentTracker(): SegmentTracker {\n return this.segmentTracker;\n }\n\n handleOnDownloadFinishEvent(event: any & DownloadFinishedEvent) {\n if (event.downloadType.indexOf('media/video') === 0) {\n const url = event.url;\n const segment: SegmentInfo = {\n name: Utils.getURLResourceName(url),\n url,\n timestamp: event.timestamp,\n };\n this.segmentTracker.addSegment(segment);\n }\n }\n\n handleSegmentPlaybackEvent = (event: any & SegmentPlaybackEvent) => {\n this.segmentTracker.removeSegment(event.url);\n };\n}\n","import type {\n Ad,\n AdBreak,\n AdBreakEvent,\n AdClickedEvent,\n AdEvent,\n AdManifestLoadedEvent,\n AdQuartileEvent,\n AdTagConfig,\n ErrorEvent,\n} from 'bitmovin-player';\n\nimport {AdModuleAPI} from '../adapters/internal/ads/AdModuleAPI';\nimport {AdAnalyticsSample} from '../types/AdAnalyticsSample';\nimport {AdBreakSample} from '../types/AdBreakSample';\nimport {AdSample} from '../types/AdSample';\nimport {Sample} from '../types/Sample';\nimport {logger} from '../utils/Logger';\nimport * as Utils from '../utils/Utils';\nimport {generateUUID} from '../utils/uuidUtils';\nimport {VERSION} from '../utils/Version';\nimport {ViewportTracker} from '../utils/ViewportTracker';\n\nimport {Analytics} from './Analytics';\n\nenum AdQuartile {\n FIRST_QUARTILE = 'firstQuartile',\n MIDPOINT = 'midpoint',\n THIRD_QUARTILE = 'thirdQuartile',\n}\n\nexport class AdAnalytics {\n static readonly MODULE_NAME = 'ads';\n private static readonly TIMEOUT_CURRENT_TIME_INTERVAL = 100;\n\n /** Boolean flag to prevent multiple calls of the {@link Event.UNLOAD} event */\n private onBeforeUnLoadEvent = false;\n private analytics: Analytics;\n private adapter: AdModuleAPI;\n private viewportTracker: ViewportTracker;\n\n private activeAdBreakSample?: AdBreakSample;\n private activeAdSample?: AdSample;\n\n private adManifestLoadedEvents: AdManifestLoadedEvent[] = [];\n private adStartupTimestamp?: number;\n private beginPlayingTimestamp?: number;\n private enterViewportTimestamp?: number;\n private isPlaying = false;\n private currentTime?: number;\n private currentTimeInterval?: number;\n private adPodPosition = 0;\n\n constructor(analytics: Analytics, adapter: AdModuleAPI) {\n this.analytics = analytics;\n this.adapter = adapter;\n\n this.adapter.adCallbacks.onAdStarted = (event) => this.onAdStarted(event);\n this.adapter.adCallbacks.onAdFinished = (event) => this.onAdFinished(event);\n this.adapter.adCallbacks.onAdBreakStarted = (event) => this.onAdBreakStarted(event);\n this.adapter.adCallbacks.onAdBreakFinished = (event) => this.onAdBreakFinished(event);\n this.adapter.adCallbacks.onAdClicked = (event) => this.onAdClicked(event);\n this.adapter.adCallbacks.onAdError = (event) => this.onAdError(event);\n this.adapter.adCallbacks.onAdManifestLoaded = (event) => this.onAdManifestLoaded(event);\n this.adapter.adCallbacks.onPlay = () => this.onPlay();\n this.adapter.adCallbacks.onPause = () => this.onPause();\n this.adapter.adCallbacks.onBeforeUnload = () => this.onBeforeUnload();\n this.adapter.adCallbacks.onAdSkipped = (event) => this.onAdSkipped(event);\n this.adapter.adCallbacks.onAdQuartile = (event) => this.onAdQuartile(event);\n\n this.viewportTracker = new ViewportTracker(this.adapter.getContainer(), () => this.onIntersectionChanged(), 0.5);\n }\n\n release() {\n this.clearCurrentTimeInterval();\n this.viewportTracker.dispose();\n }\n\n onIntersectionChanged() {\n if (!this.activeAdSample) {\n return;\n }\n if (this.isContainerInViewport()) {\n this.enterViewportTimestamp = Utils.getCurrentTimestamp();\n } else {\n if (this.enterViewportTimestamp) {\n this.activeAdSample.timeInViewport =\n (this.activeAdSample.timeInViewport || 0) + Utils.getCurrentTimestamp() - this.enterViewportTimestamp;\n }\n }\n }\n\n isContainerInViewport(): boolean {\n return this.viewportTracker ? this.viewportTracker.isInViewport() : true;\n }\n\n onPlay() {\n if (this.adapter && this.adapter.isLinearAdActive() && this.activeAdSample) {\n const timestamp = Utils.getCurrentTimestamp();\n this.beginPlayingTimestamp = timestamp;\n this.enterViewportTimestamp = timestamp;\n this.isPlaying = true;\n }\n }\n\n onPause() {\n if (this.adapter && this.adapter.isLinearAdActive() && this.activeAdSample) {\n this.updatePlayingTime(this.activeAdSample);\n this.isPlaying = false;\n }\n }\n\n onAdManifestLoaded(event: AdManifestLoadedEvent) {\n const adTagConfig = event.adConfig as AdTagConfig;\n if (adTagConfig && adTagConfig.tag && adTagConfig.tag.type === 'vmap') {\n this.sendAnalyticsRequest(new AdBreakSample(event.adConfig, event));\n } else if (event.adBreak) {\n this.adManifestLoadedEvents.push(event);\n }\n }\n\n onAdBreakStarted(event: AdBreakEvent) {\n this.adPodPosition = 0;\n this.activeAdBreakSample = new AdBreakSample(event.adBreak, this.getAdManifestLoadedEvent(event.adBreak));\n this.adStartupTimestamp = Utils.getCurrentTimestamp();\n }\n\n onAdBreakFinished(_event: AdBreakEvent) {\n this.resetActiveAd();\n this.activeAdBreakSample = undefined;\n }\n\n onAdStarted(event: AdEvent) {\n if (!event.ad.isLinear) {\n return;\n }\n\n this.resetActiveAd();\n this.activeAdSample = new AdSample(event.ad);\n this.currentTime = undefined;\n this.activeAdSample.adStartupTime = this.adStartupTimestamp\n ? Utils.getCurrentTimestamp() - this.adStartupTimestamp\n : undefined;\n\n this.startAd(this.activeAdSample);\n }\n\n onAdFinished(_event: AdEvent) {\n if (!this.activeAdBreakSample || !this.activeAdSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.completed = 1;\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.adDuration);\n }\n\n onAdSkipped(_event: AdEvent) {\n if (!this.activeAdBreakSample || !this.activeAdSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.skipped = 1;\n adSample.skipPosition = this.currentTime;\n adSample.skipPercentage = Utils.calculatePercentage(\n this.activeAdSample.skipPosition,\n this.activeAdSample.adDuration,\n );\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.skipPosition);\n }\n\n onAdError(event: ErrorEvent) {\n const {adConfig, adBreak, code, message} = event.data || {\n adBreak: undefined,\n adConfig: undefined,\n code: undefined,\n message: undefined,\n };\n\n const adBreakSample = new AdBreakSample(\n adBreak || adConfig,\n adBreak ? this.getAdManifestLoadedEvent(adBreak) : undefined,\n );\n\n adBreakSample.errorCode = code || event.code;\n adBreakSample.errorData = JSON.stringify(event.data);\n adBreakSample.errorMessage = message || event.name;\n\n let adSample;\n let errorPosition;\n if (\n this.activeAdSample &&\n adBreak &&\n adBreak.ads &&\n (adBreak.ads as any[]).includes((ad: Ad) => ad.id === (this.activeAdSample as AdSample).adId)\n ) {\n adSample = this.activeAdSample;\n errorPosition = adSample.errorPosition = this.currentTime;\n adSample.errorPercentage = Utils.calculatePercentage(adSample.errorPosition, adSample.adDuration);\n }\n this.completeAd(adBreakSample, adSample, errorPosition);\n }\n\n onAdClicked(event: AdClickedEvent) {\n if (!this.activeAdSample) {\n return;\n }\n this.activeAdSample.adClickthroughUrl = event.clickThroughUrl;\n this.activeAdSample.clicked = 1;\n this.activeAdSample.clickPosition = this.currentTime;\n this.activeAdSample.clickPercentage = Utils.calculatePercentage(\n this.activeAdSample.clickPosition,\n this.activeAdSample.adDuration,\n );\n }\n\n onAdQuartile(event: AdQuartileEvent) {\n if (!this.activeAdSample) {\n return;\n }\n if (event.quartile === AdQuartile.FIRST_QUARTILE) {\n this.activeAdSample.quartile1 = 1;\n } else if (event.quartile === AdQuartile.MIDPOINT) {\n this.activeAdSample.midpoint = 1;\n } else if (event.quartile === AdQuartile.THIRD_QUARTILE) {\n this.activeAdSample.quartile3 = 1;\n }\n }\n\n onBeforeUnload() {\n if (this.onBeforeUnLoadEvent) {\n return;\n }\n this.onBeforeUnLoadEvent = true;\n if (!this.activeAdSample || !this.activeAdBreakSample) {\n return;\n }\n\n const adSample = {...this.activeAdSample};\n adSample.closed = 1;\n adSample.closePosition = this.currentTime;\n adSample.closePercentage = Utils.calculatePercentage(adSample.closePosition, adSample.adDuration);\n this.resetActiveAd();\n this.completeAd(this.activeAdBreakSample, adSample, adSample.closePosition);\n }\n\n createNewAdAnalyticsSample(analyticsSample: Sample): AdAnalyticsSample {\n const moduleInfo = this.adapter.getAdModuleInfo();\n return {\n ...new AdAnalyticsSample(analyticsSample),\n analyticsVersion: VERSION,\n adModule: moduleInfo.name,\n adModuleVersion: moduleInfo.version,\n playerStartupTime: this.analytics.playerStartupTime,\n pageLoadTime: this.analytics.pageLoadTime,\n autoplay: this.analytics.autoplay,\n pageLoadType: Utils.getPageLoadType(),\n };\n }\n\n private getAdManifestLoadedEvent(adBreak: AdBreak) {\n if (!adBreak) {\n return undefined;\n }\n return this.adManifestLoadedEvents.find((i) => i.adBreak && i.adBreak.id === adBreak.id);\n }\n\n private sendAnalyticsRequest(adBreakSample: AdBreakSample, adSample?: AdSample) {\n const sample = {\n ...this.createNewAdAnalyticsSample(this.analytics.sample),\n ...adBreakSample,\n ...(adSample || new AdSample()),\n };\n sample.time = Utils.getCurrentTimestamp();\n sample.adImpressionId = generateUUID();\n sample.percentageInViewport = Utils.calculatePercentage(sample.timeInViewport, sample.timePlayed);\n this.analytics.backend.sendAdRequest(sample);\n }\n\n private updatePlayingTime(adSample: AdSample) {\n const timestamp = Utils.getCurrentTimestamp();\n if (this.beginPlayingTimestamp && this.isPlaying) {\n if (adSample.timePlayed !== undefined) {\n adSample.timePlayed += timestamp - this.beginPlayingTimestamp;\n }\n if (this.isContainerInViewport() && this.enterViewportTimestamp && adSample.timeInViewport !== undefined) {\n adSample.timeInViewport += timestamp - this.enterViewportTimestamp;\n }\n }\n }\n\n private startAd(adSample: AdSample) {\n adSample.started = 1;\n adSample.timePlayed = 0;\n adSample.timeInViewport = 0;\n adSample.adPodPosition = this.adPodPosition;\n const timestamp = Utils.getCurrentTimestamp();\n this.beginPlayingTimestamp = timestamp;\n this.enterViewportTimestamp = this.isContainerInViewport() ? timestamp : undefined;\n this.isPlaying = true;\n this.currentTime = 0;\n this.adPodPosition++;\n this.currentTimeInterval = window.setInterval(() => {\n try {\n if (\n adSample &&\n adSample.adDuration !== undefined &&\n adSample.adDuration > 0 &&\n this.adapter.isLinearAdActive()\n ) {\n this.currentTime = Utils.calculateTime(Math.max(this.adapter.currentTime(), 0));\n }\n } catch (e) {\n logger.log('AdStarted monitoring interval failed and got cleared', e);\n this.resetActiveAd();\n }\n }, AdAnalytics.TIMEOUT_CURRENT_TIME_INTERVAL);\n }\n\n private completeAd(adBreakSample: AdBreakSample, adSample: AdSample = new AdSample(), exitPosition?: number) {\n adSample.exitPosition = exitPosition;\n adSample.playPercentage = Utils.calculatePercentage(adSample.exitPosition, adSample.adDuration);\n\n // reset startupTimestamp for the next ad, in case there are multiple ads in one ad break\n this.adStartupTimestamp = Utils.getCurrentTimestamp();\n this.updatePlayingTime(adSample);\n this.isPlaying = false;\n this.sendAnalyticsRequest(adBreakSample, adSample);\n }\n\n private resetActiveAd() {\n this.clearCurrentTimeInterval();\n this.activeAdSample = undefined;\n }\n\n private clearCurrentTimeInterval() {\n window.clearInterval(this.currentTimeInterval);\n delete this.currentTime;\n }\n}\n","import {SsaiAdBreakMetadata, SsaiAdMetadata, SsaiAdQuartile, SsaiAdQuartileMetadata} from '../../api/AdapterAPI';\n\nexport type InternalSsaiMetadata = SsaiAdBreakMetadata & SsaiAdMetadata;\n\ntype SsaiEngagementBaseData = {\n adIndex: number;\n currentAdImpressionId: string;\n currentAdMetadata: InternalSsaiMetadata;\n type: 'error' | 'quartile' | 'started';\n};\n\nexport type SsaiEngagementErrorData = SsaiEngagementBaseData & {\n errorCode: number;\n errorMessage: string;\n timeSinceAdStartedInMs: number | undefined;\n type: 'error';\n};\n\nexport function isSsaiEngagementErrorData(data: SsaiEngagementInteractionData): data is SsaiEngagementErrorData {\n return data.type === 'error';\n}\n\nexport type SsaiEngagementQuartileData = SsaiEngagementBaseData & {\n quartile: SsaiAdQuartile;\n quartileMetadata: SsaiAdQuartileMetadata;\n timeSinceAdStartedInMs: number | undefined;\n type: 'quartile';\n};\n\nexport function isSsaiEngagementQuartileData(data: SsaiEngagementInteractionData): data is SsaiEngagementQuartileData {\n return data.type === 'quartile';\n}\n\nexport type SsaiEngagementStartedData = SsaiEngagementBaseData & {type: 'started'};\n\nexport function isSsaiEngagementStartedData(data: SsaiEngagementInteractionData): data is SsaiEngagementStartedData {\n return data.type === 'started';\n}\n\nexport type SsaiEngagementInteractionData =\n | SsaiEngagementErrorData\n | SsaiEngagementQuartileData\n | SsaiEngagementStartedData;\n","import {Subscribable} from '../../core/EventDispatcher';\nimport {CollectorConfig} from '../../types/AnalyticsConfig';\nimport {FeatureConfigContainer} from '../../types/FeatureConfigContainer';\nimport {logger} from '../../utils/Logger';\nimport {getCurrentTimestamp, isNullish} from '../../utils/Utils';\nimport {VERSION} from '../../utils/Version';\nimport {Feature} from '../Feature';\nimport {HttpRequestTracking} from '../httprequesttracking/HttpRequestTracking';\n\nimport {ErrorDetail} from './ErrorDetail';\nimport {ErrorDetailBackend} from './ErrorDetailBackend';\nimport {ErrorDetailTrackingConfig} from './ErrorDetailTrackingConfig';\nimport {OnErrorDetailEventObject} from './OnErrorDetailEventObject';\n\nexport interface ErrorDetailTrackingSettingsProvider {\n readonly licenseKey: string;\n readonly domain: string;\n readonly impressionId: string;\n readonly collectorConfig?: CollectorConfig;\n}\n\nexport class ErrorDetailTracking extends Feature<FeatureConfigContainer, ErrorDetailTrackingConfig> {\n private errorIndex = 0;\n\n constructor(\n private settingsProvider: ErrorDetailTrackingSettingsProvider,\n private backend: ErrorDetailBackend,\n private subscribables: Array<Subscribable<OnErrorDetailEventObject>>,\n private httpRequestTracking: HttpRequestTracking | undefined,\n ) {\n super();\n subscribables.forEach((subscribable) => subscribable.subscribe(this.onErrorHandler));\n }\n\n reset(): void {\n this.httpRequestTracking?.reset();\n this.errorIndex = 0;\n }\n\n enabled(): void {\n this.backend.enabled = true;\n this.backend.flush();\n }\n\n disabled(): void {\n this.errorIndex = 0;\n this.httpRequestTracking?.disable();\n this.backend.clear();\n this.subscribables.forEach((subscribable) => subscribable.unsubscribe(this.onErrorHandler));\n }\n\n configured(_authenticated: boolean, config?: ErrorDetailTrackingConfig): void {\n const maxRequests = Math.max(config?.numberOfHttpRequests ?? 0, 0);\n this.httpRequestTracking?.configure(maxRequests);\n this.backend.limitHttpRequestsOfQueuedErrorDetails(maxRequests);\n }\n\n extractConfig(configContainer: FeatureConfigContainer): ErrorDetailTrackingConfig | undefined {\n return configContainer.errorDetails;\n }\n\n private onErrorHandler = (event: OnErrorDetailEventObject) => {\n try {\n if (!this.isEnabled) {\n return;\n }\n\n const httpRequests = this.httpRequestTracking?.httpRequests;\n const httpRequestsCopy = isNullish(httpRequests) ? undefined : [...httpRequests];\n const errorIndex = this.errorIndex;\n this.errorIndex++;\n\n const errorDetail: ErrorDetail = {\n platform: 'web',\n licenseKey: this.settingsProvider.licenseKey,\n domain: this.settingsProvider.domain,\n impressionId: this.settingsProvider.impressionId,\n analyticsVersion: VERSION,\n errorId: errorIndex,\n timestamp: getCurrentTimestamp(),\n code: event.code,\n message: event.message,\n data: event.errorData ?? {\n additionalData: undefined,\n exceptionMessage: undefined,\n exceptionStacktrace: undefined,\n },\n httpRequests: httpRequestsCopy,\n };\n\n logger.log(`ErrorDetailTracking.onError: ${JSON.stringify(errorDetail)}`);\n this.backend.send(errorDetail);\n } catch (error) {\n logger.error(`ErrorDetailTracking.onError: Error in handler`, error);\n }\n };\n}\n","import {DownloadSpeedInfo} from '../types/DownloadSpeedInfo';\nimport {SpeedMeasurement} from '../types/SpeedMeasurement';\nimport {Converter} from '../utils/Converter';\n\nimport {Measure} from './Measure';\n\nexport class DownloadSpeedMeter {\n protected measures: Measure[];\n\n constructor() {\n this.measures = [];\n }\n\n reset(): void {\n this.measures = [];\n }\n\n addMeasurement(measurement: SpeedMeasurement): void {\n if (measurement.httpStatus >= 400) {\n return;\n }\n const measure = new Measure(measurement);\n\n const threshold = Converter.bitsToBytes(300 * 1000 * 1000); // 300 Megabit per second in bytes\n if (measure.speed >= threshold) {\n return;\n }\n\n this.measures.push(measure);\n }\n\n getInfo(): DownloadSpeedInfo {\n return {\n segmentsDownloadCount: this.measures.length,\n segmentsDownloadSize: this.measures.map((m) => m.size).reduce(this.add, 0),\n segmentsDownloadTime: Math.ceil(this.totalTime() * 1000),\n avgDownloadSpeed: this.avgSpeed(),\n minDownloadSpeed: this.minSpeed(),\n maxDownloadSpeed: this.maxSpeed(),\n avgTimeToFirstByte: this.avgTimeToFirstByte(),\n };\n }\n\n private add(a: number, b: number): number {\n return a + b;\n }\n\n private avgSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n const totalSpeed = this.speeds().reduce((a, b) => {\n return a + b;\n }, 0);\n const numMeasurements = this.measures.length;\n return this.bytePerSecondToBitPerSecond(totalSpeed / numMeasurements);\n }\n\n private bytePerSecondToBitPerSecond(bps: number): number {\n return Converter.bytesToBits(bps);\n }\n\n private minSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.bytePerSecondToBitPerSecond(Math.min(...this.speeds()));\n }\n\n private speeds(): number[] {\n return this.measures.map((m) => {\n return m.speed;\n });\n }\n\n private maxSpeed(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.bytePerSecondToBitPerSecond(Math.max(...this.speeds()));\n }\n\n private totalTime(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n return this.measures.reduce((a, b) => {\n return a + b.duration;\n }, 0);\n }\n\n private avgTimeToFirstByte(): number {\n if (this.measures.length === 0) {\n return 0;\n }\n const avg =\n this.measures.reduce((a, b) => {\n return a + b.timeToFirstByte * 1000;\n }, 0) / this.measures.length;\n\n return Math.ceil(avg);\n }\n}\n","import {ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD} from '../utils/Settings';\nimport * as Settings from '../utils/Settings';\nimport {isNotNullish} from '../utils/Utils';\n\nconst INITIAL_VALUE = 0;\n\nexport default class QualityChangeService {\n private qualityChangeCount = INITIAL_VALUE;\n private previousVideoBitrate = INITIAL_VALUE;\n private previousAudioBitrate = INITIAL_VALUE;\n private resetIntervalId?: number;\n private startupHasFinished = false;\n\n constructor(private qualityChangeThreshold: number = ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD) {}\n\n resetValues() {\n this.qualityChangeCount = INITIAL_VALUE;\n this.previousAudioBitrate = INITIAL_VALUE;\n this.previousVideoBitrate = INITIAL_VALUE;\n this.startupHasFinished = false;\n this.stopResetInterval();\n }\n\n isQualityChangeEventEnabled(): boolean {\n return this.qualityChangeCount <= this.qualityChangeThreshold;\n }\n\n increaseCounter() {\n this.qualityChangeCount++;\n }\n\n shouldAllowVideoQualityChange(newBitrate: number | undefined): boolean {\n return (\n this.startupHasFinished &&\n isNotNullish(newBitrate) &&\n !isNaN(newBitrate) &&\n this.previousVideoBitrate !== INITIAL_VALUE &&\n this.previousVideoBitrate !== newBitrate &&\n this.isQualityChangeEventEnabled()\n );\n }\n\n setVideoBitrate(newBitrate: number): void {\n // only bitrates after startup are relevant since some players\n // report initial bitrates before startup that differ from the\n // ones that are used after startup, which would lead to\n // wrong quality change events\n if (this.startupHasFinished) {\n this.previousVideoBitrate = newBitrate;\n }\n }\n\n setStartupHasFinished() {\n this.startupHasFinished = true;\n }\n\n shouldAllowAudioQualityChange(newBitrate: number | undefined): boolean {\n return (\n this.startupHasFinished &&\n isNotNullish(newBitrate) &&\n !isNaN(newBitrate) &&\n this.previousAudioBitrate !== INITIAL_VALUE &&\n this.previousAudioBitrate !== newBitrate &&\n this.isQualityChangeEventEnabled()\n );\n }\n\n setAudioBitrate(newBitrate: number): void {\n // only bitrates after startup are relevant since some players\n // report initial bitrates before startup that differ from the\n // ones that are used after startup, which would lead to\n // wrong quality change events\n if (this.startupHasFinished) {\n this.previousAudioBitrate = newBitrate;\n }\n }\n\n startResetInterval() {\n if (this.resetIntervalId !== undefined) {\n return;\n }\n\n this.resetIntervalId = window.setInterval(() => {\n this.resetCounter();\n }, Settings.ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL);\n }\n\n stopResetInterval() {\n if (this.resetIntervalId === undefined) {\n return;\n }\n\n window.clearInterval(this.resetIntervalId);\n delete this.resetIntervalId;\n }\n\n private resetCounter() {\n this.qualityChangeCount = 0;\n }\n}\n","/* eslint-disable perfectionist/sort-enums */\n\nexport enum PAGE_LOAD_TYPE {\n FOREGROUND = 1,\n BACKGROUND = 2,\n}\n\n/* eslint-enable perfectionist/sort-enums */\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","import {Bitmovin8Adapter} from './adapters/bitmovin8/Bitmovin8Adapter';\nimport {PlayerModule} from './adapters/bitmovin8/playerModule';\nimport {CdnProvider} from './enums/CDNProvider';\nimport {Player} from './enums/Player';\nimport {VERSION} from './utils/Version';\n\nexport {VERSION as version};\n\nexport type {AnalyticsConfig} from './types/AnalyticsConfig';\n\nexport {Player as Players};\nexport {CdnProvider as CdnProviders};\n\nexport {Bitmovin8Adapter};\n\nexport const adapters = {\n Bitmovin8Adapter,\n};\n\nexport {PlayerModule};\n\nexport default {\n PlayerModule: PlayerModule,\n};\n"],"names":["root","factory","exports","module","define","amd","self","url","body","callback","async","xhttp","isLegacyXDomainRequestUsed","window","XDomainRequest","XMLHttpRequest","responseCallback","readyState","DONE","responseText","sampleResponse","JSON","parse","onload","onreadystatechange","open","setRequestHeader","send","stringify","e","logger","error","_config","undefined","_isEnabled","this","disable","disabled","configure","authenticated","configContainer","isNotNullish","extractConfig","configured","Feature","next","nextBackend","sendRequest","sample","isPlayedAboveThreshold","sendUnloadRequest","sendRequestSynchronous","sendAdRequest","isNullish","played","LongPlaytimeFilteringBackend","videoFormatCodecMap","avc","vp9","av1","hevc","Object","getOwnPropertyNames","filter","format","some","codec","isCodecSupported","MediaSource","isTypeSupported","CodecHelper","Player","player","meter","on","PlayerEvent","DownloadFinished","event","handleOnDownloadFinishEvent","getDownloadSpeedMeter","success","downloadType","indexOf","addMeasurement","duration","downloadTime","size","timeToFirstByte","timestamp","Date","httpStatus","SpeedMeterAdapter","callbacks","subscribe","push","unsubscribe","dispatch","args","slice","forEach","index","splice","length","EventDispatcher","PlayerModule","name","Analytics","Bitmovin8Adapter","hooks","setup","config","getConfig","isConfigMissing","isAnalyticsDisabled","analytics","Promise","resolve","analyticsModuleInstance","analyticsBitmovin8Adapter","COOKIE_NAME_BITMOVIN_ANALYTICS_UUID","COOKIE_DEFAULT_MAX_AGE","collectorConfig","cookiesEnabled","deleteCookie","userId","generateUUID","existingUserId","getCookie","isBlank","cookieDomain","validateCookieDomainValue","cookiesDomain","cookieMaxAge","validateCookieMaxAgeValue","cookiesMaxAge","nowMillis","now","cookieExpires","toUTCString","setCookie","domain","expires","maxAge","SessionPersistenceHandler","value","isValidString","encodeURIComponent","isNumber","windowEventTracker","adCallbacks","AdCallbacks","isLinearAdActive","ads","getContainer","getAdModuleInfo","getModuleInfo","version","currentTime","getCurrentTime","register","Play","issuer","onPlay","Paused","onPause","AdStarted","onAdStarted","AdFinished","onAdFinished","AdBreakStarted","onAdBreakStarted","AdBreakFinished","onAdBreakFinished","AdClicked","onAdClicked","AdQuartile","onAdQuartile","AdSkipped","onAdSkipped","AdError","onAdError","AdManifestLoaded","onAdManifestLoaded","handlePageClose","onBeforeUnload","addEventListener","Bitmovin8AdModule","queue","unloadQueue","syncQueue","adQueue","flushTo","backend","QueueBackend","from","to","eventObject","EventDebugging","s","isEmpty","trim","endsWith","suffix","String","prototype","substring","startsWith","prefix","getInstance","Logger","instance","initialize","analyticsDebugConfig","log","message","enabled","console","optionalParams","table","tabularData","properties","warn","errorMessageToUser","padRight","str","Array","join","BITMOVIN_ANALYTICS_AUGMENTED_MARKER","urlPath","split","toLowerCase","MIMETypes","HLS","MP4","WEBM","DASH","_sample","NoOpBackend","Event","JSM_INITIAL_EVENT","hasAdModule","backendBaseUrl","licenseKey","analyticsCall","AnalyticsCall","key","noOp","RemoteBackend","trackedObjects","eventName","func","release","obj","pop","removeEventListener","WindowEventTracker","State","stateMachineCallbacks","playingHeartbeatService","opts","debuggingStates","enabledDebugging","getAllStatesBut","states","getAllStates","i","keys","map","createStateMachine","StateMachine","create","initial","state","SETUP","customStateMachineErrorCallback","events","SOURCE_LOADED","ERROR","SOURCE_CHANGING","INITIAL_SOURCE_CHANGE","READY","PLAY","STARTUP","PLAYING","stayIn","VIDEO_CHANGE","AUDIO_CHANGE","AD_STARTUP","VIDEOSTART_FAILED","UNLOAD","VIDEOSTART_TIMEOUT","TIMECHANGED","START_BUFFERING","END_BUFFERING","PAUSE","REBUFFERING","QUALITYCHANGE","QUALITYCHANGE_PAUSE","SEEK","PLAY_SEEKING","END_PLAY_SEEKING","SEEKED","END","SUBTITLE_CHANGE","SUBTITLE_CHANGING","AUDIOTRACK_CHANGED","AUDIOTRACK_CHANGING","START_AD","END_AD","AD_READY","AD_PAUSE","AD_PLAYING","MUTE","MUTING_READY","UN_MUTE","MUTING_PLAY","MUTING_PAUSE","START_CAST","CASTING","END_CAST","MANUAL_SOURCE_CHANGE","SOURCE_UNLOADED","QUALITYCHANGE_REBUFFERING","CUSTOM_DATA_CHANGE","CUSTOMDATACHANGE","onbeforeevent","_event","_eventTimestamp","_eventData","_from","eventTimestamp","eventData","seekDuration","seekStartTimestamp","setVideoTimeEndFromEvent","end_play_seeking","stopHeartbeat","onleavestate","logStateMachineTransition","resetRebufferingHelpers","addStatesToLog","stateDuration","onEnterStateTimestamp","lastTrackedVideoEndObject","clearVideoStartTimeout","setVideoStartTimeout","lowerCaseFrom","videoStartFailed","createVideoStartFailedReason","unload","setVideoTimeStartFromEvent","ad","defaultStateMachineCallbackFn","logMissingCallbackWarning","videoChange","audioChange","mute","unMute","startHeartbeat","_to","onenterstate","starttime","startCasting","startRebufferingHeartbeatInterval","onafterevent","initialSourceChange","manualSourceChange","stateMachine","FINISH_QUALITYCHANGE_PAUSE","FINISH_QUALITYCHANGE","FINISH_QUALITYCHANGE_REBUFFERING","FINISH_MUTING","onSsaiPlaybackInteraction","currentState","sendPlayingSample","getStates","setEnabledDebugging","AnalyticsStateMachine","Bitmovin8AnalyticsStateMachine","VERSION","Result","SUCCEEDED","NOTRANSITION","CANCELLED","PENDING","Error","INVALID_TRANSITION","PENDING_TRANSITION","INVALID_CALLBACK","WILDCARD","ASYNC","cfg","target","terminal","fsm","transitions","add","isArray","n","hasOwnProperty","buildEvent","current","is","can","transition","cannot","concat","isFinished","msg","sort","defer","doCallback","apply","beforeAnyEvent","afterAnyEvent","leaveAnyState","enterAnyState","changeState","beforeThisEvent","afterThisEvent","leaveThisState","enterThisState","beforeEvent","afterEvent","leaveState","specific","general","enterState","call","arguments","cancel","leave","defaultStateMachineCallbacks","qualityChangeService","ssaiService","SsaiService","_onLicenseKeyReceived","_onLicenseCallFailed","sourceInfoFallbackService","SourceInfoFallbackService","drmPerformanceInfo","_windowEventTracker","eventCallback","callEvent","getCurrentTimestamp","segmentsDownloadCount","segmentsDownloadSize","segmentsDownloadTime","avgDownloadSpeed","minDownloadSpeed","maxDownloadSpeed","avgTimeToFirstByte","resetIntervals","resetSourceRelatedState","getCommonPlaybackInfo","scale","devicePixelRatio","screenHeight","screen","height","screenWidth","width","clearValues","clearSegments","reset","setCustomData","values","previousState","customDataValues","customdatachange","isAudioMuted","playerIsMuted","currentVolume","InternalAdapter","DEFAULT_HEARTBEAT_INTERVAL_MS","getPlayerCurrentTime","setListener","listener","heartbeatInterval","clearHeartbeat","setInterval","onHeartbeat","clearTimeout","HeartbeatService","replace","c","r","Math","random","toString","createBackend","analyticsConfig","licensingRequest","adapter","authenticationCallback","isEnabled","inner","createInnerBackend","decorateWithDebuggingBackend","debug","DebuggingBackend","decorateWithBackendFromConfigIfAvailable","innerBackend","wrapBackend","backendUrl","ANALYTICS_BACKEND_BASE_URL","LicenseCheckingBackend","LicenseCall","sequenceNumberAssigningBackend","SequenceNumberBackend","BackendFactory","_items","offer","item","poll","shift","clear","limit","maxElements","Queue","playerVideoDuration","Number","isNaN","Infinity","streamType","streamUrl","DEFAULT_RESULT","streamFormat","progUrl","StreamTypes","dash","mpdUrl","hls","m3u8Url","prog","code","BITMOVIN_PLAYER_LICENSING_ERROR","ErrorCode","SETUP_MISSING_LICENSE_WHITELIST","QUALITY_CHANGE_THRESHOLD_EXCEEDED","BUFFERING_TIMEOUT_REACHED","VIDEO_STARTUP_TIMEOUT_REACHED","info","licenseCall","licenseKeyReceived","eventArgs","licenseLazyLoadingTimeoutHandle","unsubscribeFromAdapter","promise","wrapLicenseCheckPromiseWithCallback","performLicenseCheck","licenseCallFailed","authenticationCompleted","licenseLazyLoadingTimeout","supportsDeferredLicenseLoading","onLicenseKeyReceived","onLicenseCallFailed","setTimeout","ANALYTICS_LICENSECALL_TIMEOUT","status","LicensingResult","Denied","then","result","Granted","remoteBackend","catch","err","response","features","stateMachineEvent","VideoStartFailedReason","PLAYER_ERROR","PAGE_CLOSED","TIMEOUT","UNKNOWN","AD_TYPE","element","onIntersectionChanged","threshold","inViewport","options","rootMargin","observer","IntersectionObserver","entries","handleIntersect","observe","_error","hidden","Utils","getHiddenProp","visibilityChange","document","handleVisibilityChange","bind","isHidden","isInViewport","dispose","unobserve","disconnect","_observer","intersectionRatio","ViewportTracker","download","Measure","sanitizeBitmovin8AdapterSsaiAdBreakMetadataAdPosition","anything","maybeSsaiAdBreakMetadata","adPosition","SsaiState","eventHandler","adIndex","IDLE","isFirstSampleOfAd","sentAdQuartiles","errorSent","activate","adBreakStart","adBreakMetadata","isActivated","AD_BREAK_STARTED","currentAdMetadata","adStart","adMetadata","getTime","playerCurrentTime","reportPlaybackInteraction","ACTIVE","resetAdData","adId","adSystem","customData","currentAdImpressionId","timestampOfAdStart","getCurrentMonotonicTimestampInMs","reportEngagementInteraction","type","adQuartileFinished","adQuartile","adQuartileMetadata","includes","quartile","quartileMetadata","timeSinceAdStartedInMs","getMonotonicTimestampInMsSince","adBreakEnd","resetAdBreakData","manipulate","SSAI","customDataValuesKeys","SSAI_RELATED_SAMPLE_MARKER","sendAdEngagementErrorSample","errorCode","errorMessage","initialAnalyticsConfig","backendFactory","sessionHandler","featureManager","onErrorDetailEventDispatcher","identicalErrorReportingLimiter","pageLoadTime","playerStartupTime","videoStartupTime","autoplay","droppedSampleFrames","startupTime","featureConfigs","configureFeatures","sourceChange","guardConfigChangeAgainstMissingTitle","guardConfigChangeAgainstMissingIsLive","guardAgainstDuplicatedUserId","newConfig","mergeAnalyticsConfig","setCustomDataOnce","oldConfig","setState","sendAnalyticsRequestAndClearValues","setConfigParameters","setAutoDetectedDeviceInformation","getCurrentImpressionId","impressionId","getUserId","changeCustomData","extractCustomDataFieldsOnly","that","errorDetailTrackingSettingsProvider","getDomainFromAnalyticsConfig","licenseKeyReceivedUnsubscriber","setupSample","init","setupStateMachineCallbacks","registerFeatures","adModule","adAnalytics","AdAnalytics","getPlayerInformationFromAdapter","getPlayerName","getPlayerVersion","playerTech","getPlayerTech","resetFeatures","generateNewImpressionId","setUserId","videoCompletionTracker","resetValues","stopResetInterval","playerKey","deviceInformation","getDeviceInformationFromAnalyticsConfig","cdnProvider","videoId","videoTitle","title","customUserId","transferCustomDataFields","experimentName","model","hasWindowWebOSApi","modelName","getWebOSTVModelName","analyticsVersion","setDuration","performance","timing","loadTime","navigationStart","startup","supportedVideoCodecs","supportedVideoFormats","sanitizedStartupDuration","max","startupTimeSum","getAutoPlay","setStartupHasFinished","drmPerformance","getDrmPerformanceInfo","drmType","drmLoadTime","playing","setCompletionValues","videoStartForClosedState","videoTimeStart","videoTimeEnd","setVideoTimeStart","setVideoTimeEnd","heartbeat","heartbeatPayload","qualitychange","sendQualityChange","qualitychange_pause","qualitychange_rebuffering","setPlaybackVideoPropertiesFromEvent","setPlaybackAudioPropertiesFromEvent","audiotrack_changing","pause","paused","sendSeekingSample","seeked","seeking","paused_seeking","rebuffering","buffered","reason","videoStartFailedReason","shouldReportError","errorData","legacyData","errorSegments","segments","onError","data","CSAI","isMuted","subtitle_changing","analyticsEventBase","calculateTime","end","_duration","_state","videoPlaybackWidth","videoPlaybackHeight","bitrate","videoBitrate","videoCodec","audioBitrate","audioCodec","setPlaybackInfoFromAdapter","getCurrentPlaybackInfo","isLive","videoDuration","videoWindowWidth","videoWindowHeight","isBoolean","isCasting","castTech","audioLanguage","subtitleEnabled","subtitleLanguage","droppedFrames","platform","pageLoadType","getPageLoadType","path","sanitizePath","location","pathname","language","navigator","userLanguage","userAgent","PlayerSize","Window","time","completedTotal","sendAnalyticsRequest","customDataOnceValues","downloadSpeedInfo","setQualityInfoOnSample","copySample","sendSsaiEngagementAdSample","ssaiEngagementTrackingEnabled","isSsaiEngagementStartedData","ssaiAdSample","createStartedAdSample","isSsaiEngagementQuartileData","createQuartileAdSample","isSsaiEngagementErrorData","ssaiErrorAdSample","createErrorAdSample","completed","addWatched","start","getCompletionPercentage","startResetInterval","increaseCounter","isQualityChangeEventEnabled","FeatureManager","IdenticalErrorReportingLimiter","playbackInfo","CdnProvider","HttpRequestType","clicked","closed","midpoint","quartile1","quartile3","skipped","started","adClickthroughUrl","clickThroughUrl","id","mediaUrl","mediaFileUrl","mediaUrlDetails","getHostnameAndPathFromUrl","mediaPath","mediaServer","hostname","isLinear","adPlaybackHeight","adPlaybackWidth","mimeType","advertiser","advertiserName","apiFramework","creative","creativeAdId","creativeId","universalAdId","universalAdIdRegistry","idRegistry","universalAdIdValue","adDescription","minSuggestedDuration","calculateTimeWithUndefined","survey","surveyUrl","uri","adTitle","wrapperAdsCount","wrapperAdIds","linearAd","adSkipAfter","AdSample","parseSkipAfter","skippableAfter","adSkippable","skippable","adDuration","skipAfter","MESSAGE_NAMESPACE","ANALYTICS_VIDEOSTART_TIMEOUT","ANALYTICS_QUALITY_CHANGE_COUNT_THRESHOLD","ANALYTICS_QUALITY_CHANGE_COUNT_RESET_INTERVAL","ANALYTICS_REBUFFER_TIMEOUT","ANALYTICS_MIN_SEEK_DIFFERENCE_THRESHOLD","SEQUENCE_NUMBER_LIMIT","ssai","isDefined","internalAdapter","adBreakMetadataWithValidAdPosition","hasValidSsaiAdBreakMetadataStructure","sanitizedAdBreakMetadata","simplySanitizeSsaiAdBreakMetadata","hasValidSsaiAdMetadataStructure","sanitizedAdMetadata","simplySanitizeSsaiAdMetadata","hasValidSsaiAdQuartileStructure","sanitizedSsaiAdQuartileMetadata","sanitizeSsaiAdQuartileMetadata","hasPlayerAlreadyBeenAugmented","markPlayerInstanceAsAugmented","playerConfig","sanitizedConfig","sanitizeAnalyticsConfig","Bitmovin8InternalAdapter","wrapPlayerLoad","originalLoad","load","casting","muting_ready","setStreamFormat","applyStreamFormat","applyAndStoreCodecInfo","codecInfo","attributes","newCookie","cookie","cname","charAt","hiddenProp","PAGE_LOAD_TYPE","BACKGROUND","FOREGROUND","toBoolean","Boolean","valueOf","isObject","isPlainObject","timeInSeconds","round","getCustomDataString","fromConfig","toConfig","CustomDataUtils","customDataFieldCount","customDataField","getDocumentPropWithPrefix","prop","pascalCase","toUpperCase","isVideoInFullscreen","fullscreenProp","nodeName","domElement","createElement","href","calculatePercentage","numerator","denominator","getURLResourceName","joinUrls","reduce","prev","substr","getSourceInfoFromBitmovinSourceConfig","progressive","progBitrate","playbackVideoData","getPlaybackVideoData","progressiveArrayIndex","baseUrl","licenseServerUrl","post","analyticsServerUrl","adAnalyticsServerUrl","analyticsUrl","isSsaiRelatedSample","appendSsaiRoutingParam","trySendBeacon","fallbackFunction","requestHeaders","sendBeacon","blob","Blob","adSample","adAnalyticsUrl","_issuer","match","input","retVal","bytesToBits","bytes","bitsToBytes","bits","kiloBitsToBits","kiloBits","Converter","videoImpressionId","AdAnalyticsSample","CastTech","addSegment","segment","removeSegment","getSegments","SegmentTracker","isAdPosition","maybeSsaiAdMetadata","ssaiAdMetadata","sanitizedCustomDataValues","extracted","isSsaiAdQuartile","ssaiAdQuartileMetadata","failedBeaconUrl","ViewMode","speedMeter","segmentTracker","httpRequestTrackingAdapter","onBeforeUnLoadEvent","BITMOVIN","getPlayerType","getInfo","_adModule","isAdPlaying","lastTrackedCurrentTime","currentAd","getActiveAd","registerPlayerEventListeners","registerUnloadEventListeners","ssaiEngagementInteractionData","requestTracking","HttpRequestTracking","ErrorDetailTracking","ErrorDetailBackend","errorDetailSubscribable","playback","getViewMode","Fullscreen","normalizeVideoDuration","getStreamType","offsetWidth","offsetHeight","getAudio","lang","getSource","getDroppedVideoFrames","applySubtitleProperties","applyPlaybackQualityProperties","applyCastingProperties","applySourceProperties","callManualSourceChangeEvent","SourceUnloaded","SourceLoaded","getDuration","setVideoDuration","CastStarted","CastStopped","Playing","TimeChanged","Seek","allowSeeking","Seeked","StallStarted","StallEnded","AudioPlaybackQualityChanged","audioQualityChangedData","sourceQuality","targetQuality","shouldAllowAudioQualityChange","setAudioBitrate","VideoPlaybackQualityChanged","videoQualityChangedData","shouldAllowVideoQualityChange","setVideoBitrate","ViewModeChanged","START_FULLSCREEN","END_FULLSCREEN","Muted","Unmuted","additionalData","PlaybackFinished","AudioChanged","SubtitleEnabled","SubtitleDisabled","LicenseValidated","handleCollectorUnload","Destroy","source","progSourceInfo","enabledSubtitle","subtitles","list","find","videoQuality","audioQuality","getPlaybackAudioData","isAirplayActive","AirPlay","remoteControlConfig","remotecontrol","GoogleCast","WebSocket","seekEvent","abs","position","seekTarget","AnalyticsSettings","DownloadSpeedMeter","SegmentTrackerAdapter","getSegmentTracker","HttpRequestTrackingAdapter","TimespanOverlappingType","watched","overlappingTimespan","mergeWatched","w","time1","k","time2","overlapType","getOverlappingType","Overlapping","mergeAndReplace","getOverlappingTimespan","FirstContainedInSecond","SecondContainedInFirst","None","first","second","isMomentInTimespan","moment","timespan","firstIndex","secondIndex","newWatchedTimespan","unregisterFeatures","feature","constructor","adConfig","adManifestLoadedEvent","adFallbackIndex","manifestDownloadTime","downloadTiming","adReplaceContentDuration","replaceContentDuration","currentFallbackIndex","adBreakConfig","adOffset","adPreloadOffset","preloadOffset","adTagConfig","adIsPersistent","persistent","tag","fallbackTags","adTagType","adTagUrl","adTagDetails","adTagServer","adTagPath","adBreak","adScheduleTime","scheduleTime","adIdPlayer","AdBreakSample","underlying","sequenceNumber","updateSampleBeforeSending","isSequenceNumberAboveThreshold","fields","debugFields","printFields","f","eventDispatcher","playerExports","onDownloadFinished","httpRequest","mapHttpRequestType","REBUFFERING_HEARTBEAT_INTERVALS","videoStartupTimeoutMs","Settings","rebufferTimeoutMs","currentRebufferingIntervalIndex","stateMachineEventMethod","playbackCurrentTimeInSeconds","clearRebufferingTimeoutHandle","clearRebufferingHeartbeatHandle","startRebufferingTimeoutHandle","rebufferingHeartbeatIntervalHandle","min","clearInterval","rebufferingTimeoutHandle","videoStartTimeout","triggeredBySsai","payload","_queue","_enabled","copyErrorDetailTruncateStringsAndUrls","errorDetail","maxStringLength","maxUrlLength","copyErrorDataTruncateStrings","httpRequests","request","copyHttpRequestTruncateUrls","maxLength","lastRedirectLocation","exceptionMessage","copyErrorDetailTruncateHttpRequests","maxRequests","limitHttpRequestsOfQueuedErrorDetails","errorDetailCopy","MAX_STRING_LENGTH","MAX_URL_LENGTH","flush","copy","removeFromQueue","findIndex","_currentErrorCount","_lastErrorCode","MAX_IDENTICAL_ERROR_REPORTING","subscribables","_maxRequests","DEFAULT_MAX_REQUESTS","_httpRequestQueue","onDownloadFinishedHandler","addRequest","subscribable","items","adType","ROUTING_URL_PARAM","ROUTING_URL_PARAM_VALUE_SSAI","playbackSample","ssaiEngagementErrorData","buildAdSample","ssaiEngagementStartedData","ssaiEngagementQuartileData","timestampInMs","adEngagementSample","customData1","customData2","customData3","customData4","customData5","customData6","customData7","customData8","customData9","customData10","customData11","customData12","customData13","customData14","customData15","customData16","customData17","customData18","customData19","customData20","customData21","customData22","customData23","customData24","customData25","customData26","customData27","customData28","customData29","customData30","customData31","customData32","customData33","customData34","customData35","customData36","customData37","customData38","customData39","customData40","customData41","customData42","customData43","customData44","customData45","customData46","customData47","customData48","customData49","customData50","adImpressionId","quartile1FailedBeaconUrl","midpointFailedBeaconUrl","quartile3FailedBeaconUrl","completedFailedBeaconUrl","floor","excludedStates","stateEnumObj","whileIn","stateMachineEventDefBuilderFn","runEventCallbacksFor","passOver","_ex","loggerMessage","loggerMessageData","ignoreStates","ignoredState","stateStringEnumObj","deviceType","deviceClass","origin","oldConfigWithoutSourceRelatedFields","sourceSpecificProperties","customDataFieldsRegex","removeSourceRelatedFields","mergedCollectorConfig","oldCollectorConfig","newCollectorConfig","mergeCollectorConfig","webOSSystem","deviceInfo","PalmSystem","handleSegmentPlaybackEvent","SegmentPlayback","adManifestLoadedEvents","isPlaying","adPodPosition","viewportTracker","clearCurrentTimeInterval","activeAdSample","isContainerInViewport","enterViewportTimestamp","timeInViewport","beginPlayingTimestamp","updatePlayingTime","activeAdBreakSample","getAdManifestLoadedEvent","adStartupTimestamp","resetActiveAd","adStartupTime","startAd","completeAd","skipPosition","skipPercentage","errorPosition","adBreakSample","errorPercentage","clickPosition","clickPercentage","FIRST_QUARTILE","MIDPOINT","THIRD_QUARTILE","closePosition","closePercentage","createNewAdAnalyticsSample","analyticsSample","moduleInfo","adModuleVersion","percentageInViewport","timePlayed","currentTimeInterval","TIMEOUT_CURRENT_TIME_INTERVAL","exitPosition","playPercentage","MODULE_NAME","settingsProvider","httpRequestTracking","errorIndex","onErrorHandler","httpRequestsCopy","errorId","exceptionStacktrace","_authenticated","numberOfHttpRequests","errorDetails","measures","measurement","measure","speed","m","ceil","totalTime","avgSpeed","minSpeed","maxSpeed","a","b","totalSpeed","speeds","numMeasurements","bytePerSecondToBitPerSecond","bps","avg","qualityChangeThreshold","qualityChangeCount","previousVideoBitrate","previousAudioBitrate","startupHasFinished","newBitrate","resetIntervalId","resetCounter","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__","adapters"],"sourceRoot":""}