{"version":3,"sources":["/home/ubuntu24-new/Dev/stormcloud-vp/lib/players/HlsPlayer.cjs","../../src/players/HlsPlayer.tsx","../../src/sdk/hlsAdPlayer.ts","../../src/utils/devUrl.ts","../../src/sdk/pal.ts","../../src/utils/mqttClient.ts","../../src/utils/mqttConfig.ts","../../src/utils/vastEnvironmentSignals.ts","../../src/utils/tracking.ts","../../src/utils/polyfills.ts","../../src/utils/vastMacros.ts","../../src/utils/browserCompat.ts","../../src/player/Scte35Parser.ts","../../src/player/Scte35CueManager.ts","../../src/player/AdConfigManager.ts","../../src/player/AdTimingService.ts","../../src/player/PlaceholderLayer.ts","../../src/player/HlsEngine.ts","../../src/player/PlayerControls.ts"],"names":["__create","Object","create","__defProp","defineProperty","__getOwnPropNames","getPrototypeOf","__getOwnPropDesc","getOwnPropertyDescriptor","getOwnPropertyNames","__getProtoOf","__hasOwnProp","prototype","hasOwnProperty","__export","target","all","name","get","enumerable","__copyProps","to","from","except","desc","key","call","mod","isNodeMode","__esModule","value","__toCommonJS","HlsPlayer_exports","default","HlsPlayer","module","exports","import_react","listeners","adVideoElement","Map","require","import_hls","__toESM","MAX_VAST_WRAPPER_DEPTH","createHlsAdPlayer","contentVideo","options","adPlaying","originalMutedState","originalVolume","Math","max","min","volume","mainHlsInstance","adHls","adContainerEl","currentAd","podAds","sessionId","preloadingAds","STALL_TIMEOUT_MS","STALL_CHECK_INTERVAL_MS","stallWatchdogId","lastAdProgressTime","lastAdProgressPosition","trackingFired","impression","set","start","firstQuartile","thirdQuartile","complete","emit","event","payload","Array","fn","error","urls","console","log","trackingUrl","generateSessionId","Date","now","random","toString","substr","fireTrackingPixels","length","forEach","url","includes","licenseKey","img","Image","src","warn","levels","currentLevel","autoLevel","loadLevel","level","width","height","bitrate","selectBestMediaFile","mediaFiles","Error","firstFile","mainQuality","getMainStreamQuality","scoredFiles","map","file","widthDiff","abs","heightDiff","resolutionDiff","fileBitrate","bitrateDiff","score","sort","a","b","bestMatch","resolution","isHlsMediaFile","mediaFile","type","toLowerCase","isProgressiveMediaFile","startsWith","endsWith","createEmptyTrackingUrls","midpoint","mute","unmute","pause","resume","fullscreen","exitFullscreen","skip","extractTrackingUrls","scope","trackingUrls","querySelectorAll","el","textContent","trim","push","getAttribute","eventKey","mergeTrackingUrls","source","keys","concat","parseVastXml","xmlString","xmlDoc","parser","DOMParser","parseFromString","parserError","querySelector","adElement","adId","title","clickThrough","wrapperUri","vastAdTagUri","isNoAdAvailable","durationText","durationParts","split","duration","parseInt","mediaFileElements","mf","index","bitrateAttr","bitrateValue","ad","parseAdElement","id","fetchVastXml","vastTagUrl","credentials","requestVast","response","creds","fetch","mode","headers","referrerPolicy","ok","statusText","text","fetchAndParseVastAd","depth","accumulatedTracking","vastXml","parsed","substring","fetchAndParsePod","adElements","ads","resolved","bSeq","aSeq","aVal","Number","isFinite","MAX_SAFE_INTEGER","bVal","createAdVideoElement","document","createElement","video","style","position","left","top","objectFit","backgroundColor","playsInline","muted","setupAdEventListeners","addEventListener","noteAdProgress","progress","currentTime","startStallWatchdog","podIndex","advanceToNextPodAd","handleAdComplete","e","handleAdError","ended","setAdPlayingFlag","isPlaying","dataset","stormcloudAdPlaying","resetQuartileTracking","preserveImpression","loadCurrentAdMedia","isHlsAd","Hls","isSupported","destroy","enableWorker","lowLatencyMode","loadSource","attachMedia","on","Events","MANIFEST_PARSED","play","catch","ERROR","_event","data","fatal","canPlayType","load","total","clearStallWatchdog","handleAdStall","window","setInterval","paused","releaseAdDecoder","remove","display","pointerEvents","continueLiveStreamDuringAds","visibility","opacity","initialize","container","right","bottom","justifyContent","zIndex","parentElement","appendChild","requestAds","preloaded","Promise","reject","preloadedAds","has","delete","resolve","contentVolume","stop","previousMutedState","destroyed","pendingTimeouts","timeoutId","clearTimeout","removeChild","clear","isAdPlaying","resize","listener","Set","add","off","updateOriginalMutedState","nextVolume","isNaN","getOriginalMutedState","getOriginalVolume","setAdVolume","clamped","getAdVolume","showPlaceholder","alignItems","hidePlaceholder","getLoadedAdDuration","getLoadedAdId","getPodAdCount","getPodTotalDurationMs","reduce","PRIVATE_HOST_PATTERNS","isLocalDevHost","hostname","host","replace","some","pattern","test","toDevSafeUrl","rawUrl","URL","protocol","cleanPath","pathname","PAL_SDK_URL","_nonceLoader","_palLoadPromise","loadPalSdk","goog","pal","existing","timeout","setTimeout","script","async","setAttribute","onload","onerror","head","getOrCreateNonceLoader","consentSettings","ConsentSettings","allowStorage","NonceLoader","createPalNonceManager","currentNonce","currentNonceManager","generateNonce","loader","request","manager","NonceRequest","adWillAutoPlay","adWillPlayMuted","playerVolume","continuousPlayback","descriptionUrl","location","href","iconsSupported","playerType","playerVersion","supportedApiFrameworks","videoWidth","videoHeight","ppid","JSON","stringify","clearReconnectTimer","openConnection","loadNonceManager","getNonce","getCurrentNonce","injectNonce","searchParams","base","sep","encodeURIComponent","sendPlaybackStart","sendPlaybackEnd","sendAdClick","sendAdTouch","reset","DEFAULT_MQTT_CONFIG","enabled","brokerAddress","brokerPort","wsPort","username","password","topicPrefix","qos","mqttConfig","applyMQTTConfig","overrides","assign","isMQTTEnabled","buildMQTTBrokerUrl","brokerUrl","buildPlayerTopic","channel","import_mqtt","LOG","KEEPALIVE_SECONDS","CONNECT_TIMEOUT_MS","RECONNECT_BASE_MS","RECONNECT_MAX_MS","MAX_RECONNECT_ATTEMPTS","COOLDOWN_MS","client","status","reconnectAttempts","reconnectTimer","stopped","teardownClient","removeAllListeners","end","scheduleReconnect","delay","jitter","floor","clientId","timerVariant","slice","mqtt","connect","keepalive","reconnectPeriod","err","info","message","ensureMQTTClient","publishMQTT","initMQTTClient","topic","connected","publish","AIRY_WEBOS_APP_ID","AIRY_ANDROID_APP_ID","AIRY_TIZEN_APP_ID","AIRY_ROKU_APP_ID","AIRY_APP_NAME","PLAYER_ID_STORAGE_KEY","LG_TEST_APP_ID","LG_TEST_CONTENT_URL","_lgTestDeviceId","getLgTestDeviceId","createUuid","isLgWebOS","navigator","getDefaultAppId","ua","DEVICE_ID_STORAGE_KEYS","platformLat","bridgeSignals","deviceId","limitAdTracking","platformDevice","ANDROID_ID_TYPES","resolveVastEnvironmentSignals","isCtv","readNativeBridgeSignals","readPlatformNativeDeviceId","lg","deviceIdType","readStoredString","inferDeviceIdType","readStoredLimitAdTracking","appId","appName","LG_TEST_APP_NAME","getOrCreateCtvSessionId","userAgent","isEquivalentDeviceIdType","tagType","runtimeType","tag","runtime","resolveNativeDeviceId","readStoredDeviceId","isMacroPlaceholder","isZeroedAdId","getOrCreateStoredUuid","storageKey","readPersistentId","writePersistentId","CTV_SESSION_STORAGE_KEY","readCookie","localStorage","setItem","writeCookie","PERSISTENT_ID_COOKIE_MAX_AGE","prefix","parts","part","entry","decodeURIComponent","cookie","bytes","crypto","randomUUID","getRandomValues","seed","performanceNow","i","hex","padStart","performance","adinfo","webapis","tifa","getTIFA","lat","isLATEnabled","webOSDev","lgudid","LGUDID","roku","Roku","rida","getPublisherUniqueId","ZEROED_AD_ID_PATTERNS","t","candidates","__STORMCLOUD_CTV_AD_INFO__","__STORMCLOUD_CTV__","stormcloudCtv","AiryTV","Android","webOS","tizen","amazon","filter","Boolean","contentUrl","readBridgeValue","readBridgeBoolean","result","normalized","normalizeBoolean","getItem","cachedBrowserId","buildAnalyticsContext","config","context","debugAdTiming","isLiveStream","inputStreamType","getClientInfo","screen","platform","vendor","maxTouchPoints","memory","deviceMemory","hardwareConcurrency","screenInfo","availWidth","availHeight","orientation","pixelDepth","deviceType","brand","os","model","isSmartTV","isAndroid","isWebView","isWebApp","webosMatch","match","tizenMatch","tvMatch","androidModelMatch","outerHeight","outerWidth","matchMedia","matches","standalone","angle","domain","origin","path","language","languages","join","cookieEnabled","doNotTrack","referrer","visibilityState","sha256Hex","input","encodedData","utf8","buffer","hashBuffer","hash","char","fallbackHash","timestamp","subtle","digest","Uint8Array","TextEncoder","encode","unescape","charCodeAt","padEnd","resolvePlayerIdentitySeed","clientInfo","nativeDeviceId","persistedId","getBrowserID","canPublish","buildPlayerMetricEvent","flags","playerId","captureAt","toISOString","player_id","device_type","ad_loaded","adLoaded","ad_detect","adDetect","capture_at","input_stream_type","publishTracking","body","sendInitialTracking","metricEvent","events","sendAdDetectTracking","adDetectInfo","sendHeartbeat","sendAdLoadedTracking","adLoadedInfo","sendAdImpressionTracking","adImpressionInfo","ad_played_count","heartbeatData","polyfillURLSearchParams","URLSearchParams","URLSearchParamsPolyfill","init","params","parseQueryString","append","query","cleanQuery","param","decodedKey","safeDecodeURIComponent","decodedValue","str","values","String","getAll","callback","polyfillTextEncoder","TextEncoderPolyfill","encoding","charcode","polyfillPromiseFinally","finally","constructor","then","reason","polyfillObjectAssign","sources","TypeError","nextSource","nextKey","polyfillArrayFrom","arrayLike","mapFn","thisArg","items","len","polyfillStringStartsWith","polyfillStringEndsWith","polyfillStringIncludes","search","pos","indexOf","initializePolyfills","UNEXPANDED_MACRO_PATTERN","INVALID_VAST_PARAM_KEY","EXAMPLE_COM_URL","CTV_UNSUPPORTED_PARAMS","INLINE_DEVICE_MACRO_REPLACEMENTS","ctx","getValue","correlator","trimmed","generateCorrelator","buf","Uint32Array","expandInlineMacroPlaceholders","baseUrl","applyDeviceIdentityParams","runtimeId","tagRdid","tagLat","latValue","tagRdidValid","tagTypeValid","removeBrokenAppNameOrphans","toDelete","_value","suffix","normalizeVastTagUrl","raw","anValue","orphanFragments","reconstructed","_match","val","applyVastMacros","expandedUrl","replaceCorrelatorFallback","streamCorrelator","pod","podMaxDurationMs","round","podMaxAds","requestUrl","pageUrl","existingUrl","success","consent","correlatorRegex","deviceTypeHint","gdpr","gdprConsent","usPrivacy","adTest","staleKeys","fetchConsentSignals","timeoutMs","signals","tasks","tcfApi","__tcfapi","settled","tcData","eventStatus","gdprApplies","tcString","uspApi","__uspapi","uspString","getChromeVersion","getWebKitVersion","getPlatform","userAgentData","detectBrowser","version","majorVersion","isLegacyTV","supportsModernJS","webOSVersion","tizenVersion","chromeVersionNum","chromeVersion","webkitVersion","getBrowserConfigOverrides","browser","allowNativeHls","pauseContentDuringAds","logBrowserInfo","debug","parseCueOutDuration","num","parseFloat","dStr","d","parseCueOutCont","res","elapsedMatch","durationMatch","elapsed","slashMatch","parseAttributeList","attrs","regex","rawVal","toNumber","isManifestBasedMarker","marker","id3","splice_command_type","decodeId3ValueToText","decoder","TextDecoder","decode","out","fromCharCode","getFragmentStartSeconds","frag","startPTS","candidate","parseScte35FromId3","cueOutMatch","arg","dur","ptsSeconds","durationSeconds","cueOutContMatch","cont","cueInMatch","daterangeMatch","hasScteOut","hasScteIn","klass","bin","normalizeFragmentPayload","ArrayBuffer","isView","view","byteOffset","byteLength","detectTsPacketFormat","packetSizes","packetSize","tsPayloadOffset","offset","matchedPackets","packetStart","getPsiSectionStart","payloadUnitStart","pointerField","sectionStart","getPsiSectionLength","parsePatSection","pmtPids","sectionLength","sectionEnd","programNumber","pid","descriptorsIdentifyScte35","descriptorStart","descriptorEnd","registration","parsePmtSection","tsScte35Pids","programInfoLength","streamType","elementaryPid","esInfoLength","hasProcessedTsScte35Section","section","processedSections","checksum","size","firstKey","next","addScte35SectionMarker","markers","parseScte35Binary","appendScte35Bytes","assemblers","assembler","expectedLength","collectScte35SectionsFromPayload","previousAssembler","subarray","tableId","totalLength","parseScte35FromTsPackets","packetInfo","sectionAssemblers","tsStart","secondByte","thirdByte","fourthByte","adaptationFieldControl","hasPayload","payloadStart","adaptationLength","payloadEnd","BitReader","bytePos","bitPos","readBits","numBits","remainingInByte","toRead","currentByte","shift","mask","bits","skipBits","n","bytePosition","readSpliceTime","r","ptsAdjustmentTicks","timeSpecifiedFlag","ptsTicks","high","low","markerTypeFromSegmentationTypeId","segmentationTypeId","parseScte35SegmentationDescriptor","descriptor","identifier","segmentationEventId","cancelIndicator","programSegmentationFlag","segmentationDurationFlag","componentCount","durationTicks","segmentationUpidLength","markerType","parseScte35SegmentationDescriptors","descriptorLoopLength","descriptorOffset","descriptorLength","descriptorDataStart","descriptorDataEnd","descriptorTag","descriptorMarker","ptsAdjHigh","ptsAdjLow","spliceCommandLength","spliceCommandType","commandBodyStart","spliceEventId","cancel","outOfNetwork","programSpliceFlag","durationFlag","spliceImmediateFlag","componentPtsSeconds","expectedDescriptorOffset","splice_event_id","segmentation_event_id","Scte35CueManager","callbacks","pendingScte35Cues","recentScte35CueKeys","recentScte35CueLimit","processedTsScte35Sections","pendingScte35CueKey","pendingScte35CueKeyValue","activeScte35BreakKey","activeScte35BreakKeyValue","scheduledScte35BreakKey","scheduledScte35BreakKeyValue","createScte35CueContext","readiness","sn","fragmentSn","fragmentStartSec","fragmentStartSeconds","onScte35Cue","cue","createScte35Cue","pendingKey","getPendingScte35CueKey","onEarlyStartCue","shouldAcceptScte35EndCue","inAdBreak","isInAdBreak","hasRecentlyHandledScte35Cue","markScte35CueHandled","onPlaybackCue","activatePendingScte35CuesForFragment","matchingCues","entries","getScte35CueKey","getScte35MarkerRaw","toIdentityString","daterangeId","ID","scteValue","isStrongScte35CueKey","recentKey","trimRecentScte35CueMaps","AdConfigManager","vmapBreaks","consumedVmapBreakIds","viewCorrelator","consentSignals","podCounter","podAssignedByPrefetch","lastHeartbeatTime","defaultPodMaxAds","defaultPodMaxDurationMs","isVmapEnabled","isVmap","vmapUrl","fetchAdConfiguration","vastMode","vastEndpoint","apiUrl","imaPayload","decodedPayload","numberAds","fetchAndParseVmap","apiVastTagUrl","json","applyMqttConfigFromResponse","ima","vast","cue_tones","number_ads","apiNumberAds","mqtt_config","vmapXml","parseVmapToBreaks","doc","VMAP_NS","adBreakNodes","getElementsByTagNameNS","getElementsByTagName","localName","node","timeOffsetRaw","startTimeMs","parseVmapTimeOffsetToMs","adTagNode","adTagUrl","seconds","millis","breakId","aStart","bStart","timeOffset","hms","hh","mm","ss","ms","hours","minutes","percent","ratio","durationSec","getAdBreakKey","adBreak","resolveBreakStartMs","schedule","breakStartMs","findBreakForTime","findCurrentOrNextBreak","nowMs","tol","driftToleranceMs","durationMs","podMinDurationMs","selectVastTagsForBreak","s","beginNewAdPod","resolvePodParams","breakDurationMs","maxDurationMs","maxAds","minDurationMs","podExactDuration","generatePodVastUrl","podParams","adPlayer","envSignals","urlWithMacros","ctvAdRequest","autoplay","finalUrl","palNonce","sendHeartbeatIfNeeded","initializeTracking","heartbeatInterval","activeAdRequestToken","globalNoFillThreshold","globalNoFillCooldownUntil","destroyTracking","clearInterval","AdTimingService","adRequestWatchdogToken","adFailsafeToken","ptsDriftEmaMs","adBreakPlayedDurationMs","adBreakEpoch","adRequestTokenCounter","currentAdIndex","totalAdsInBreak","totalAdRequestsInBreak","maxTotalAdRequestsPerBreak","lastAdRequestTime","consecutiveFailures","maxConsecutiveFailures","minAdRequestIntervalMs","backoffBaseMs","maxBackoffMs","defaultMinRemainingMsToStartAd","failedVastUrls","temporaryFailureCooldownMs","globalConsecutiveNoFills","globalNoFillBackoffBaseMs","globalNoFillBackoffMaxMs","globalLastGamRequestTime","globalMinGamIntervalMs","scheduleAdStopCountdown","remainingMs","ensureAdStoppedByTimer","adStopTimerId","nowWallClockMs","alpha","sampleMs","clearAdStopTimer","onAdStopTimerFired","scheduleAdStartIn","delayMs","clearAdStartTimer","onAdStartTimerFired","cueKey","adStartTimerId","updatePtsDrift","ptsSecondsSample","resolveScteBreakStartWallClockMs","estimatedCurrentPtsMs","deltaMs","setAdBreakDurationBoundary","expectedAdBreakDurationMs","currentAdBreakStartWallClockMs","scteAdBreakEndWallClockMs","scheduleAdStopAtBreakBoundary","getLoadedAdDurationMs","adFitsRemainingBudget","getWallClockRemainingAdMs","endWallClockMs","getAdBreakEndWallClockMs","getDurationBudgetRemainingMs","adController","logAdDurationDecision","accepted","remainingBudget","recordPlayedAdDuration","ensureLoadedAdFitsBudget","fits","rejectLoadedAdForDuration","markAdStarted","notePodAdStarted","getRemainingAdMs","wallClockRemaining","budgetRemaining","getMinRemainingMsToStartAd","configured","minRemainingMsToStartAd","hasTimeToStartAnotherAd","minRemaining","isTemporaryAdError","isUrlInCooldown","failureTime","temporaryFailureUrls","cleanupTemporaryFailures","isGamInCooldown","recordGamNoFill","exponent","backoff","pow","resetGamNoFillCounter","enforceGlobalRateLimit","waitMs","startAdRequestWatchdog","token","clearAdRequestWatchdog","adRequestWatchdogId","logAdState","onWatchdogTimeout","startAdFailsafeTimer","clearAdFailsafeTimer","failsafeMs","adFailsafeTimeoutMs","adFailsafeTimerId","videoPaused","onFailsafeTimeout","extra","showAds","resetForBreakEnd","PlaceholderLayer","ensureContainer","transition","offsetHeight","show","wasHidden","requestAnimationFrame","hide","HlsEngine","cueManager","timing","nativeHlsMode","videoSrcProtection","reloadingLiveStream","bufferedSegmentsCount","shouldAutoplayAfterBuffering","hasInitialBufferCompleted","shouldUseNativeHls","getStreamType","canNative","setupNativeHls","adBehavior","isLive","setupHls","hls","import_hls2","backBufferLength","liveDurationInfinity","maxLiveSyncPlaybackRate","liveSyncDuration","maxBufferLength","maxMaxBufferLength","maxBufferSize","maxBufferHole","highBufferWatchdogPeriod","nudgeOffset","nudgeMaxRetry","startPosition","MEDIA_ATTACHED","_","_data","minSegments","details","live","onManifestParsed","minSegmentsBeforePlay","LEVEL_LOADED","_evt","hasPendingAdBreak","fragments","fragmentsToScan","tagList","isArray","idx","earlyDetection","FRAG_BUFFERED","FRAG_PARSING_METADATA","id3Tags","samples","pts","onId3Tag","FRAG_LOADED","processFragmentScte35Payload","FRAG_DECRYPTED","FRAG_CHANGED","activatePendingCuesForFragment","prog","ErrorTypes","NETWORK_ERROR","startLoad","MEDIA_ERROR","recoverMediaError","onFatalDestroy","payloadData","getLiveSyncPosition","liveSyncPosition","restartLoadAt","stopLoad","reloadLiveStream","detachMedia","removeAttribute","getAdAudioVolume","toggleMute","newMutedState","restoreVolume","toggleFullscreen","fullscreenElement","requestFullscreen","setMuted"],"mappings":"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","sourcesContent":["\"use strict\";\nvar __create = Object.create;\nvar __defProp = Object.defineProperty;\nvar __getOwnPropDesc = Object.getOwnPropertyDescriptor;\nvar __getOwnPropNames = Object.getOwnPropertyNames;\nvar __getProtoOf = Object.getPrototypeOf;\nvar __hasOwnProp = Object.prototype.hasOwnProperty;\nvar __export = (target, all) => {\n  for (var name in all)\n    __defProp(target, name, { get: all[name], enumerable: true });\n};\nvar __copyProps = (to, from, except, desc) => {\n  if (from && typeof from === \"object\" || typeof from === \"function\") {\n    for (let key of __getOwnPropNames(from))\n      if (!__hasOwnProp.call(to, key) && key !== except)\n        __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });\n  }\n  return to;\n};\nvar __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(\n  // If the importer is in node compatibility mode or this is not an ESM\n  // file that has been converted to a CommonJS file using a Babel-\n  // compatible transform (i.e. \"__esModule\" has not been set), then set\n  // \"default\" to the CommonJS \"module.exports\" for node compatibility.\n  isNodeMode || !mod || !mod.__esModule ? __defProp(target, \"default\", { value: mod, enumerable: true }) : target,\n  mod\n));\nvar __toCommonJS = (mod) => __copyProps(__defProp({}, \"__esModule\", { value: true }), mod);\n\n// src/players/HlsPlayer.tsx\nvar HlsPlayer_exports = {};\n__export(HlsPlayer_exports, {\n  default: () => HlsPlayer\n});\nmodule.exports = __toCommonJS(HlsPlayer_exports);\nvar import_react = require(\"react\");\n\n// src/sdk/hlsAdPlayer.ts\nvar import_hls = __toESM(require(\"hls.js\"), 1);\nvar MAX_VAST_WRAPPER_DEPTH = 5;\nfunction createHlsAdPlayer(contentVideo, options) {\n  let adPlaying = false;\n  let originalMutedState = false;\n  let originalVolume = Math.max(0, Math.min(1, contentVideo.volume || 1));\n  const listeners = /* @__PURE__ */ new Map();\n  const licenseKey = options?.licenseKey;\n  const mainHlsInstance = options?.mainHlsInstance;\n  let adVideoElement;\n  let adHls;\n  let adContainerEl;\n  let currentAd;\n  let podAds = [];\n  let podIndex = 0;\n  let sessionId;\n  const preloadedAds = /* @__PURE__ */ new Map();\n  const preloadingAds = /* @__PURE__ */ new Map();\n  let destroyed = false;\n  let pendingTimeouts = [];\n  const STALL_TIMEOUT_MS = 4e3;\n  const STALL_CHECK_INTERVAL_MS = 1e3;\n  let stallWatchdogId;\n  let lastAdProgressTime = 0;\n  let lastAdProgressPosition = 0;\n  let trackingFired = {\n    impression: false,\n    start: false,\n    firstQuartile: false,\n    midpoint: false,\n    thirdQuartile: false,\n    complete: false\n  };\n  function emit(event, payload) {\n    const set = listeners.get(event);\n    if (!set) return;\n    for (const fn of Array.from(set)) {\n      try {\n        fn(payload);\n      } catch (error) {\n        console.warn(\n          `[HlsAdPlayer] Error in event listener for ${event}:`,\n          error\n        );\n      }\n    }\n  }\n  function generateSessionId() {\n    return `session-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;\n  }\n  function fireTrackingPixels(urls) {\n    if (!urls || urls.length === 0) return;\n    urls.forEach((url) => {\n      try {\n        let trackingUrl = url;\n        if (sessionId) {\n          trackingUrl = `${trackingUrl}${trackingUrl.includes(\"?\") ? \"&\" : \"?\"}session_id=${sessionId}`;\n        }\n        if (licenseKey) {\n          trackingUrl = `${trackingUrl}${trackingUrl.includes(\"?\") ? \"&\" : \"?\"}license_key=${licenseKey}`;\n        }\n        const img = new Image(1, 1);\n        img.src = trackingUrl;\n        console.log(`[HlsAdPlayer] Fired tracking pixel: ${trackingUrl}`);\n      } catch (error) {\n        console.warn(`[HlsAdPlayer] Error firing tracking pixel:`, error);\n      }\n    });\n  }\n  function getMainStreamQuality() {\n    if (!mainHlsInstance || !mainHlsInstance.levels) {\n      return null;\n    }\n    const currentLevel = mainHlsInstance.currentLevel;\n    if (currentLevel === -1 || !mainHlsInstance.levels[currentLevel]) {\n      const autoLevel = mainHlsInstance.loadLevel;\n      if (autoLevel !== -1 && mainHlsInstance.levels[autoLevel]) {\n        const level2 = mainHlsInstance.levels[autoLevel];\n        return {\n          width: level2.width || 1920,\n          height: level2.height || 1080,\n          bitrate: level2.bitrate || 5e6\n        };\n      }\n      return null;\n    }\n    const level = mainHlsInstance.levels[currentLevel];\n    return {\n      width: level.width || 1920,\n      height: level.height || 1080,\n      bitrate: level.bitrate || 5e6\n    };\n  }\n  function selectBestMediaFile(mediaFiles) {\n    if (mediaFiles.length === 0) {\n      throw new Error(\"No media files available\");\n    }\n    const firstFile = mediaFiles[0];\n    if (!firstFile) {\n      throw new Error(\"No media files available\");\n    }\n    if (mediaFiles.length === 1) {\n      return firstFile;\n    }\n    const mainQuality = getMainStreamQuality();\n    if (!mainQuality) {\n      console.log(\n        \"[HlsAdPlayer] No main stream quality info, using first media file\"\n      );\n      return firstFile;\n    }\n    console.log(\"[HlsAdPlayer] Main stream quality:\", mainQuality);\n    const scoredFiles = mediaFiles.map((file) => {\n      const widthDiff = Math.abs(file.width - mainQuality.width);\n      const heightDiff = Math.abs(file.height - mainQuality.height);\n      const resolutionDiff = widthDiff + heightDiff;\n      const fileBitrate = (file.bitrate || 5e3) * 1e3;\n      const bitrateDiff = Math.abs(fileBitrate - mainQuality.bitrate);\n      const score = resolutionDiff * 2 + bitrateDiff / 1e3;\n      return { file, score, resolutionDiff, bitrateDiff };\n    });\n    scoredFiles.sort((a, b) => a.score - b.score);\n    const bestMatch = scoredFiles[0];\n    if (!bestMatch) {\n      console.log(\"[HlsAdPlayer] No best match found, using first media file\");\n      return firstFile;\n    }\n    console.log(\"[HlsAdPlayer] Selected media file:\", {\n      url: bestMatch.file.url,\n      resolution: `${bestMatch.file.width}x${bestMatch.file.height}`,\n      bitrate: bestMatch.file.bitrate,\n      score: bestMatch.score,\n      resolutionDiff: bestMatch.resolutionDiff,\n      bitrateDiff: bestMatch.bitrateDiff\n    });\n    return bestMatch.file;\n  }\n  function isHlsMediaFile(mediaFile) {\n    const type = mediaFile.type.toLowerCase();\n    const url = mediaFile.url.toLowerCase();\n    return type === \"application/x-mpegurl\" || type === \"application/vnd.apple.mpegurl\" || type.includes(\"mpegurl\") || url.includes(\".m3u8\");\n  }\n  function isProgressiveMediaFile(mediaFile) {\n    const type = mediaFile.type.toLowerCase();\n    const url = mediaFile.url.toLowerCase();\n    return type.startsWith(\"video/\") || url.endsWith(\".mp4\") || url.includes(\".mp4?\");\n  }\n  function createEmptyTrackingUrls() {\n    return {\n      impression: [],\n      start: [],\n      firstQuartile: [],\n      midpoint: [],\n      thirdQuartile: [],\n      complete: [],\n      mute: [],\n      unmute: [],\n      pause: [],\n      resume: [],\n      fullscreen: [],\n      exitFullscreen: [],\n      skip: [],\n      error: []\n    };\n  }\n  function extractTrackingUrls(scope) {\n    const trackingUrls = createEmptyTrackingUrls();\n    scope.querySelectorAll(\"Impression\").forEach((el) => {\n      const url = el.textContent?.trim();\n      if (url) trackingUrls.impression.push(url);\n    });\n    scope.querySelectorAll(\"Tracking\").forEach((el) => {\n      const event = el.getAttribute(\"event\");\n      const url = el.textContent?.trim();\n      if (event && url) {\n        const eventKey = event;\n        if (trackingUrls[eventKey]) {\n          trackingUrls[eventKey].push(url);\n        }\n      }\n    });\n    scope.querySelectorAll(\"Error\").forEach((el) => {\n      const url = el.textContent?.trim();\n      if (url) trackingUrls.error.push(url);\n    });\n    return trackingUrls;\n  }\n  function mergeTrackingUrls(target, source) {\n    Object.keys(target).forEach((key) => {\n      if (source[key] && source[key].length > 0) {\n        target[key] = target[key].concat(source[key]);\n      }\n    });\n    return target;\n  }\n  function parseVastXml(xmlString) {\n    try {\n      const parser = new DOMParser();\n      const xmlDoc = parser.parseFromString(xmlString, \"text/xml\");\n      const parserError = xmlDoc.querySelector(\"parsererror\");\n      if (parserError) {\n        console.error(\n          \"[HlsAdPlayer] XML parsing error (malformed VAST XML):\",\n          parserError.textContent\n        );\n        return { type: \"empty\" };\n      }\n      const adElement = xmlDoc.querySelector(\"Ad\");\n      if (!adElement) {\n        console.warn(\"[HlsAdPlayer] No Ad element found in VAST XML\");\n        return { type: \"empty\" };\n      }\n      const adId = adElement.getAttribute(\"id\") || \"unknown\";\n      const title = xmlDoc.querySelector(\"AdTitle\")?.textContent || \"Ad\";\n      const clickThrough = xmlDoc.querySelector(\"ClickThrough\")?.textContent?.trim();\n      const wrapperUri = xmlDoc.querySelector(\"VASTAdTagURI\")?.textContent?.trim();\n      if (wrapperUri) {\n        console.log(\n          `[HlsAdPlayer] VAST wrapper detected, following VASTAdTagURI: ${wrapperUri}`\n        );\n        return {\n          type: \"wrapper\",\n          vastAdTagUri: wrapperUri,\n          trackingUrls: extractTrackingUrls(xmlDoc),\n          clickThrough\n        };\n      }\n      const isNoAdAvailable = adId === \"empty\" || title.toLowerCase().includes(\"no ad available\") || title.toLowerCase() === \"no ad available\";\n      const durationText = xmlDoc.querySelector(\"Duration\")?.textContent || \"00:00:30\";\n      const durationParts = durationText.split(\":\");\n      const duration = parseInt(durationParts[0] || \"0\", 10) * 3600 + parseInt(durationParts[1] || \"0\", 10) * 60 + parseInt(durationParts[2] || \"0\", 10);\n      const mediaFileElements = xmlDoc.querySelectorAll(\"MediaFile\");\n      const mediaFiles = [];\n      console.log(\n        `[HlsAdPlayer] Found ${mediaFileElements.length} MediaFile element(s) in VAST XML`\n      );\n      mediaFileElements.forEach((mf, index) => {\n        const type = mf.getAttribute(\"type\") || \"\";\n        const url = mf.textContent?.trim() || \"\";\n        const width = mf.getAttribute(\"width\") || \"\";\n        const height = mf.getAttribute(\"height\") || \"\";\n        console.log(\n          `[HlsAdPlayer] MediaFile ${index}: type=\"${type}\", url=\"${url}\", width=\"${width}\", height=\"${height}\"`\n        );\n        const mediaFile = {\n          url,\n          type,\n          width: parseInt(width || \"1920\", 10),\n          height: parseInt(height || \"1080\", 10),\n          bitrate: void 0\n        };\n        if (!url) {\n          console.warn(`[HlsAdPlayer] MediaFile ${index} has empty URL`);\n          return;\n        }\n        const bitrateAttr = mf.getAttribute(\"bitrate\");\n        const bitrateValue = bitrateAttr ? parseInt(bitrateAttr, 10) : void 0;\n        mediaFile.bitrate = bitrateValue && bitrateValue > 0 ? bitrateValue : void 0;\n        if (isHlsMediaFile(mediaFile) || isProgressiveMediaFile(mediaFile)) {\n          mediaFiles.push(mediaFile);\n          console.log(\n            `[HlsAdPlayer] Added ${isHlsMediaFile(mediaFile) ? \"HLS\" : \"progressive\"} MediaFile: ${url}`\n          );\n        } else {\n          console.log(\n            `[HlsAdPlayer] MediaFile ${index} ignored (type=\"${type}\" is not supported)`\n          );\n        }\n      });\n      if (mediaFiles.length === 0) {\n        if (isNoAdAvailable) {\n          console.warn(\n            \"[HlsAdPlayer] No ads available (VAST response indicates no ads)\"\n          );\n        } else {\n          console.warn(\"[HlsAdPlayer] No supported media files found in VAST XML\");\n        }\n        return { type: \"empty\" };\n      }\n      return {\n        type: \"inline\",\n        ad: {\n          id: adId,\n          title,\n          duration,\n          mediaFiles,\n          trackingUrls: extractTrackingUrls(xmlDoc),\n          clickThrough\n        }\n      };\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Error parsing VAST XML:\", error);\n      return { type: \"empty\" };\n    }\n  }\n  function parseAdElement(adElement) {\n    try {\n      const adId = adElement.getAttribute(\"id\") || \"unknown\";\n      const title = adElement.querySelector(\"AdTitle\")?.textContent || \"Ad\";\n      const clickThrough = adElement.querySelector(\"ClickThrough\")?.textContent?.trim();\n      const wrapperUri = adElement.querySelector(\"VASTAdTagURI\")?.textContent?.trim();\n      if (wrapperUri) {\n        return {\n          type: \"wrapper\",\n          vastAdTagUri: wrapperUri,\n          trackingUrls: extractTrackingUrls(adElement),\n          clickThrough\n        };\n      }\n      const isNoAdAvailable = adId === \"empty\" || title.toLowerCase().includes(\"no ad available\") || title.toLowerCase() === \"no ad available\";\n      const durationText = adElement.querySelector(\"Duration\")?.textContent || \"00:00:30\";\n      const durationParts = durationText.split(\":\");\n      const duration = parseInt(durationParts[0] || \"0\", 10) * 3600 + parseInt(durationParts[1] || \"0\", 10) * 60 + parseInt(durationParts[2] || \"0\", 10);\n      const mediaFileElements = adElement.querySelectorAll(\"MediaFile\");\n      const mediaFiles = [];\n      mediaFileElements.forEach((mf) => {\n        const type = mf.getAttribute(\"type\") || \"\";\n        const url = mf.textContent?.trim() || \"\";\n        const width = mf.getAttribute(\"width\") || \"\";\n        const height = mf.getAttribute(\"height\") || \"\";\n        if (!url) return;\n        const bitrateAttr = mf.getAttribute(\"bitrate\");\n        const bitrateValue = bitrateAttr ? parseInt(bitrateAttr, 10) : void 0;\n        const mediaFile = {\n          url,\n          type,\n          width: parseInt(width || \"1920\", 10),\n          height: parseInt(height || \"1080\", 10),\n          bitrate: bitrateValue && bitrateValue > 0 ? bitrateValue : void 0\n        };\n        if (isHlsMediaFile(mediaFile) || isProgressiveMediaFile(mediaFile)) {\n          mediaFiles.push(mediaFile);\n        }\n      });\n      if (mediaFiles.length === 0) {\n        if (isNoAdAvailable) {\n          console.warn(\n            \"[HlsAdPlayer] Pod <Ad> indicates no ad available\"\n          );\n        } else {\n          console.warn(\"[HlsAdPlayer] No supported media files in pod <Ad>\");\n        }\n        return { type: \"empty\" };\n      }\n      return {\n        type: \"inline\",\n        ad: {\n          id: adId,\n          title,\n          duration,\n          mediaFiles,\n          trackingUrls: extractTrackingUrls(adElement),\n          clickThrough\n        }\n      };\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Error parsing pod <Ad> element:\", error);\n      return { type: \"empty\" };\n    }\n  }\n  async function fetchVastXml(vastTagUrl, credentials = \"include\") {\n    const requestVast = (creds) => fetch(vastTagUrl, {\n      mode: \"cors\",\n      credentials: creds,\n      headers: {\n        \"Accept\": \"application/xml, text/xml, */*\"\n      },\n      referrerPolicy: \"no-referrer-when-downgrade\"\n    });\n    let response;\n    try {\n      response = await requestVast(credentials);\n    } catch (error) {\n      if (credentials !== \"omit\") {\n        console.warn(\n          `[HlsAdPlayer] VAST fetch failed with credentials=\"${credentials}\", retrying without credentials:`,\n          error\n        );\n        response = await requestVast(\"omit\");\n      } else {\n        throw error;\n      }\n    }\n    if (!response.ok) {\n      throw new Error(`Failed to fetch VAST: ${response.statusText}`);\n    }\n    return response.text();\n  }\n  async function fetchAndParseVastAd(vastTagUrl, depth = 0, accumulatedTracking = createEmptyTrackingUrls()) {\n    const vastXml = await fetchVastXml(\n      vastTagUrl,\n      depth === 0 ? \"include\" : \"omit\"\n    );\n    console.log(\"[HlsAdPlayer] VAST XML received\");\n    console.log(\n      \"[HlsAdPlayer] VAST XML content (first 2000 chars):\",\n      vastXml.substring(0, 2e3)\n    );\n    const parsed = parseVastXml(vastXml);\n    if (parsed.type === \"empty\") {\n      return null;\n    }\n    if (parsed.type === \"wrapper\") {\n      if (depth >= MAX_VAST_WRAPPER_DEPTH) {\n        console.warn(\n          `[HlsAdPlayer] VAST wrapper depth limit (${MAX_VAST_WRAPPER_DEPTH}) reached, aborting redirect chain`\n        );\n        return null;\n      }\n      mergeTrackingUrls(accumulatedTracking, parsed.trackingUrls);\n      return fetchAndParseVastAd(\n        parsed.vastAdTagUri,\n        depth + 1,\n        accumulatedTracking\n      );\n    }\n    mergeTrackingUrls(parsed.ad.trackingUrls, accumulatedTracking);\n    return parsed.ad;\n  }\n  async function fetchAndParsePod(vastTagUrl) {\n    const vastXml = await fetchVastXml(vastTagUrl);\n    console.log(\"[HlsAdPlayer] Pod VAST XML received\");\n    const parser = new DOMParser();\n    const xmlDoc = parser.parseFromString(vastXml, \"text/xml\");\n    if (xmlDoc.querySelector(\"parsererror\")) {\n      console.error(\"[HlsAdPlayer] Pod VAST XML parsing error (malformed)\");\n      return [];\n    }\n    const adElements = Array.from(xmlDoc.querySelectorAll(\"Ad\"));\n    if (adElements.length === 0) {\n      console.warn(\"[HlsAdPlayer] No <Ad> elements found in pod VAST response\");\n      return [];\n    }\n    adElements.sort((a, b) => {\n      const aSeq = parseInt(a.getAttribute(\"sequence\") || \"\", 10);\n      const bSeq = parseInt(b.getAttribute(\"sequence\") || \"\", 10);\n      const aVal = Number.isFinite(aSeq) ? aSeq : Number.MAX_SAFE_INTEGER;\n      const bVal = Number.isFinite(bSeq) ? bSeq : Number.MAX_SAFE_INTEGER;\n      return aVal - bVal;\n    });\n    const ads = [];\n    for (const adElement of adElements) {\n      const parsed = parseAdElement(adElement);\n      if (parsed.type === \"inline\") {\n        ads.push(parsed.ad);\n      } else if (parsed.type === \"wrapper\") {\n        try {\n          const resolved = await fetchAndParseVastAd(\n            parsed.vastAdTagUri,\n            1,\n            parsed.trackingUrls\n          );\n          if (resolved) {\n            ads.push(resolved);\n          }\n        } catch (error) {\n          console.warn(\n            \"[HlsAdPlayer] Failed to resolve wrapper <Ad> in pod:\",\n            error\n          );\n        }\n      }\n    }\n    console.log(`[HlsAdPlayer] Parsed ${ads.length} ad(s) from pod VAST response`);\n    return ads;\n  }\n  function createAdVideoElement() {\n    const video = document.createElement(\"video\");\n    video.style.position = \"absolute\";\n    video.style.left = \"0\";\n    video.style.top = \"0\";\n    video.style.width = \"100%\";\n    video.style.height = \"100%\";\n    video.style.objectFit = \"contain\";\n    video.style.backgroundColor = \"#000\";\n    video.playsInline = true;\n    video.muted = false;\n    video.volume = 1;\n    console.log(\n      `[HlsAdPlayer] Created ad video element with volume ${video.volume}`\n    );\n    return video;\n  }\n  function setupAdEventListeners() {\n    if (!adVideoElement || !currentAd) return;\n    adVideoElement.addEventListener(\"timeupdate\", () => {\n      if (!currentAd || !adVideoElement) return;\n      noteAdProgress();\n      const progress = adVideoElement.currentTime / currentAd.duration;\n      if (progress >= 0.25 && !trackingFired.firstQuartile) {\n        trackingFired.firstQuartile = true;\n        fireTrackingPixels(currentAd.trackingUrls.firstQuartile);\n      }\n      if (progress >= 0.5 && !trackingFired.midpoint) {\n        trackingFired.midpoint = true;\n        fireTrackingPixels(currentAd.trackingUrls.midpoint);\n      }\n      if (progress >= 0.75 && !trackingFired.thirdQuartile) {\n        trackingFired.thirdQuartile = true;\n        fireTrackingPixels(currentAd.trackingUrls.thirdQuartile);\n      }\n    });\n    adVideoElement.addEventListener(\"playing\", () => {\n      startStallWatchdog();\n      if (!currentAd || trackingFired.start) return;\n      trackingFired.start = true;\n      fireTrackingPixels(currentAd.trackingUrls.start);\n      console.log(\"[HlsAdPlayer] Ad started playing\");\n    });\n    adVideoElement.addEventListener(\"ended\", () => {\n      if (!currentAd || trackingFired.complete) return;\n      trackingFired.complete = true;\n      fireTrackingPixels(currentAd.trackingUrls.complete);\n      console.log(\"[HlsAdPlayer] Ad completed\");\n      if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n        return;\n      }\n      handleAdComplete();\n    });\n    adVideoElement.addEventListener(\"error\", (e) => {\n      if (!adPlaying) return;\n      console.error(\"[HlsAdPlayer] Ad video error:\", e);\n      if (currentAd) {\n        fireTrackingPixels(currentAd.trackingUrls.error);\n      }\n      if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n        return;\n      }\n      handleAdError();\n    });\n    adVideoElement.addEventListener(\"volumechange\", () => {\n      if (!currentAd) return;\n      if (adVideoElement.muted) {\n        fireTrackingPixels(currentAd.trackingUrls.mute);\n      } else {\n        fireTrackingPixels(currentAd.trackingUrls.unmute);\n      }\n    });\n    adVideoElement.addEventListener(\"pause\", () => {\n      if (currentAd && !adVideoElement.ended) {\n        fireTrackingPixels(currentAd.trackingUrls.pause);\n      }\n    });\n    adVideoElement.addEventListener(\"play\", () => {\n      if (currentAd && adVideoElement.currentTime > 0) {\n        fireTrackingPixels(currentAd.trackingUrls.resume);\n      }\n    });\n  }\n  function setAdPlayingFlag(isPlaying) {\n    if (isPlaying) {\n      contentVideo.dataset.stormcloudAdPlaying = \"true\";\n    } else {\n      delete contentVideo.dataset.stormcloudAdPlaying;\n    }\n  }\n  function resetQuartileTracking(preserveImpression) {\n    trackingFired = {\n      impression: preserveImpression ? trackingFired.impression : false,\n      start: false,\n      firstQuartile: false,\n      midpoint: false,\n      thirdQuartile: false,\n      complete: false\n    };\n  }\n  function loadCurrentAdMedia() {\n    if (!adVideoElement || !currentAd) {\n      throw new Error(\"No ad video element or ad to load\");\n    }\n    const mediaFile = selectBestMediaFile(currentAd.mediaFiles);\n    if (!mediaFile) {\n      throw new Error(\"No media file available for ad\");\n    }\n    const isHlsAd = isHlsMediaFile(mediaFile);\n    console.log(\n      `[HlsAdPlayer] Loading ${isHlsAd ? \"HLS\" : \"progressive\"} ad (pod ${podIndex + 1}/${podAds.length || 1}) from: ${mediaFile.url}`\n    );\n    if (isHlsAd && import_hls.default.isSupported()) {\n      if (adHls) {\n        adHls.destroy();\n      }\n      adHls = new import_hls.default({\n        enableWorker: true,\n        lowLatencyMode: false\n      });\n      adHls.loadSource(mediaFile.url);\n      adHls.attachMedia(adVideoElement);\n      adHls.on(import_hls.default.Events.MANIFEST_PARSED, () => {\n        console.log(\"[HlsAdPlayer] HLS manifest parsed, starting playback\");\n        adVideoElement.play().catch((error) => {\n          console.error(\"[HlsAdPlayer] Error starting ad playback:\", error);\n          handleAdError();\n        });\n      });\n      adHls.on(import_hls.default.Events.ERROR, (_event, data) => {\n        console.error(\"[HlsAdPlayer] HLS error:\", data);\n        if (data.fatal) {\n          handleAdError();\n        }\n      });\n    } else if (isHlsAd && adVideoElement.canPlayType(\"application/vnd.apple.mpegurl\")) {\n      adVideoElement.src = mediaFile.url;\n      adVideoElement.play().catch((error) => {\n        console.error(\"[HlsAdPlayer] Error starting ad playback:\", error);\n        handleAdError();\n      });\n    } else if (!isHlsAd && isProgressiveMediaFile(mediaFile)) {\n      if (adHls) {\n        adHls.destroy();\n        adHls = void 0;\n      }\n      adVideoElement.src = mediaFile.url;\n      adVideoElement.load();\n      adVideoElement.play().catch((error) => {\n        console.error(\"[HlsAdPlayer] Error starting progressive ad playback:\", error);\n        handleAdError();\n      });\n    } else {\n      throw new Error(`Unsupported ad media file type: ${mediaFile.type}`);\n    }\n  }\n  function advanceToNextPodAd() {\n    if (podIndex >= podAds.length - 1) {\n      return false;\n    }\n    podIndex++;\n    currentAd = podAds[podIndex];\n    resetQuartileTracking(false);\n    if (currentAd) {\n      fireTrackingPixels(currentAd.trackingUrls.impression);\n      trackingFired.impression = true;\n      console.log(\n        `[HlsAdPlayer] Advancing to next pod ad (${podIndex + 1}/${podAds.length}): ${currentAd.title}, duration: ${currentAd.duration}s`\n      );\n    }\n    try {\n      loadCurrentAdMedia();\n      emit(\"pod_ad_started\", { index: podIndex, total: podAds.length });\n      return true;\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Failed to load next pod ad:\", error);\n      return false;\n    }\n  }\n  function clearStallWatchdog() {\n    if (stallWatchdogId != null) {\n      clearInterval(stallWatchdogId);\n      stallWatchdogId = void 0;\n    }\n  }\n  function noteAdProgress() {\n    lastAdProgressTime = Date.now();\n    if (adVideoElement) {\n      lastAdProgressPosition = adVideoElement.currentTime;\n    }\n  }\n  function handleAdStall() {\n    console.warn(\n      \"[HlsAdPlayer] Ad playback stalled (no progress) - recovering to avoid a blank frame\"\n    );\n    clearStallWatchdog();\n    if (currentAd) {\n      fireTrackingPixels(currentAd.trackingUrls.error);\n    }\n    if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n      return;\n    }\n    handleAdError();\n  }\n  function startStallWatchdog() {\n    clearStallWatchdog();\n    noteAdProgress();\n    stallWatchdogId = window.setInterval(() => {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n      if (adVideoElement.currentTime > lastAdProgressPosition + 0.05) {\n        noteAdProgress();\n        return;\n      }\n      if (adVideoElement.paused) {\n        noteAdProgress();\n        return;\n      }\n      if (Date.now() - lastAdProgressTime >= STALL_TIMEOUT_MS) {\n        handleAdStall();\n      }\n    }, STALL_CHECK_INTERVAL_MS);\n  }\n  function releaseAdDecoder() {\n    if (adHls) {\n      adHls.destroy();\n      adHls = void 0;\n    }\n    if (adVideoElement) {\n      adVideoElement.pause();\n      adVideoElement.removeAttribute(\"src\");\n      try {\n        adVideoElement.load();\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] adVideoElement.load() threw after src removal:\", error);\n      }\n      adVideoElement.remove();\n      adVideoElement = void 0;\n    }\n    if (adContainerEl) {\n      adContainerEl.style.display = \"none\";\n      adContainerEl.style.pointerEvents = \"none\";\n    }\n  }\n  function handleAdComplete() {\n    console.log(\"[HlsAdPlayer] Handling ad completion\");\n    clearStallWatchdog();\n    adPlaying = false;\n    setAdPlayingFlag(false);\n    contentVideo.muted = true;\n    releaseAdDecoder();\n    if (!options?.continueLiveStreamDuringAds) {\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n    }\n    if (options?.continueLiveStreamDuringAds) {\n      if (contentVideo.paused) {\n        console.log(\"[HlsAdPlayer] Content video paused in live mode, resuming playback\");\n        contentVideo.play().catch((error) => {\n          console.error(\"[HlsAdPlayer] Error resuming content playback in live mode:\", error);\n        });\n      } else {\n        console.log(\"[HlsAdPlayer] Content video already playing in live mode\");\n      }\n    }\n    emit(\"content_resume\");\n  }\n  function handleAdError() {\n    console.log(\"[HlsAdPlayer] Handling ad error\");\n    clearStallWatchdog();\n    adPlaying = false;\n    setAdPlayingFlag(false);\n    contentVideo.muted = true;\n    releaseAdDecoder();\n    if (!options?.continueLiveStreamDuringAds) {\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n    }\n    emit(\"ad_error\");\n  }\n  return {\n    initialize() {\n      console.log(\"[HlsAdPlayer] Initializing\");\n      if (!adContainerEl) {\n        const container = document.createElement(\"div\");\n        container.style.position = \"absolute\";\n        container.style.left = \"0\";\n        container.style.top = \"0\";\n        container.style.right = \"0\";\n        container.style.bottom = \"0\";\n        container.style.display = \"none\";\n        container.style.alignItems = \"center\";\n        container.style.justifyContent = \"center\";\n        container.style.pointerEvents = \"none\";\n        container.style.zIndex = \"30\";\n        container.style.backgroundColor = \"#000\";\n        contentVideo.parentElement?.appendChild(container);\n        adContainerEl = container;\n      }\n    },\n    async requestAds(vastTagUrl) {\n      console.log(\"[HlsAdPlayer] Requesting ads:\", vastTagUrl);\n      if (adPlaying) {\n        console.warn(\n          \"[HlsAdPlayer] Cannot request new ads while an ad is playing\"\n        );\n        return Promise.reject(new Error(\"Ad already playing\"));\n      }\n      try {\n        sessionId = generateSessionId();\n        let ads = [];\n        if (preloadedAds.has(vastTagUrl)) {\n          const preloaded = preloadedAds.get(vastTagUrl);\n          preloadedAds.delete(vastTagUrl);\n          if (preloaded) {\n            ads = [preloaded];\n          }\n          console.log(\n            \"[HlsAdPlayer] Using preloaded VAST response:\",\n            vastTagUrl\n          );\n        } else {\n          ads = await fetchAndParsePod(vastTagUrl);\n        }\n        if (!ads.length) {\n          console.warn(\"[HlsAdPlayer] No ads available from VAST response\");\n          emit(\"ad_error\");\n          return Promise.reject(new Error(\"No ads available from VAST response\"));\n        }\n        podAds = ads;\n        podIndex = 0;\n        currentAd = ads[0];\n        console.log(\n          `[HlsAdPlayer] Pod parsed: ${ads.length} ad(s), first=\"${currentAd?.title}\", duration=${currentAd?.duration}s`\n        );\n        if (currentAd) {\n          fireTrackingPixels(currentAd.trackingUrls.impression);\n          trackingFired.impression = true;\n        }\n        return Promise.resolve();\n      } catch (error) {\n        console.error(\"[HlsAdPlayer] Error requesting ads:\", error);\n        emit(\"ad_error\");\n        return Promise.reject(error);\n      }\n    },\n    async play() {\n      if (!currentAd) {\n        console.warn(\n          \"[HlsAdPlayer] Cannot play: No ad loaded (no ads available)\"\n        );\n        return Promise.reject(new Error(\"No ad loaded\"));\n      }\n      console.log(\"[HlsAdPlayer] Starting ad playback\");\n      try {\n        if (!adVideoElement) {\n          adVideoElement = createAdVideoElement();\n          adContainerEl?.appendChild(adVideoElement);\n          setupAdEventListeners();\n        }\n        resetQuartileTracking(true);\n        const contentVolume = contentVideo.volume;\n        originalVolume = Math.max(\n          0,\n          Math.min(1, contentVolume || originalVolume)\n        );\n        if (!options?.continueLiveStreamDuringAds) {\n          contentVideo.pause();\n          console.log(\"[HlsAdPlayer] Content paused (VOD mode)\");\n        } else {\n          console.log(\"[HlsAdPlayer] Content continues (Live mode)\");\n        }\n        console.log(\"[HlsAdPlayer] FORCE MUTING main video\");\n        contentVideo.muted = true;\n        adPlaying = true;\n        setAdPlayingFlag(true);\n        if (adVideoElement) {\n          adVideoElement.volume = Math.max(0, Math.min(1, originalVolume));\n          adVideoElement.muted = originalMutedState;\n          console.log(\n            `[HlsAdPlayer] Set ad video volume to ${adVideoElement.volume}, muted: ${adVideoElement.muted}, originalMutedState: ${originalMutedState}, contentVolume: ${contentVolume}`\n          );\n        }\n        if (adContainerEl) {\n          adContainerEl.style.display = \"flex\";\n          adContainerEl.style.pointerEvents = \"auto\";\n        }\n        emit(\"content_pause\");\n        loadCurrentAdMedia();\n        return Promise.resolve();\n      } catch (error) {\n        console.error(\"[HlsAdPlayer] Error playing ad:\", error);\n        handleAdError();\n        return Promise.reject(error);\n      }\n    },\n    pause() {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n      try {\n        if (adVideoElement && !adVideoElement.paused) {\n          adVideoElement.pause();\n        }\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] Error pausing ad:\", error);\n      }\n    },\n    resume() {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n      try {\n        if (adVideoElement && adVideoElement.paused) {\n          adVideoElement.play().catch(() => {\n          });\n        }\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] Error resuming ad:\", error);\n      }\n    },\n    async stop() {\n      console.log(\"[HlsAdPlayer] Stopping ad\");\n      clearStallWatchdog();\n      adPlaying = false;\n      setAdPlayingFlag(false);\n      const previousMutedState = contentVideo.muted;\n      contentVideo.muted = originalMutedState;\n      contentVideo.volume = Math.max(0, Math.min(1, originalVolume));\n      console.log(\n        `[HlsAdPlayer] Restored mute state on stop: ${previousMutedState} -> ${originalMutedState}, volume: ${contentVideo.volume}`\n      );\n      releaseAdDecoder();\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n      if (options?.continueLiveStreamDuringAds) {\n        if (contentVideo.paused) {\n          console.log(\"[HlsAdPlayer] Content video paused in live mode, resuming playback on stop\");\n          contentVideo.play().catch((error) => {\n            console.error(\"[HlsAdPlayer] Error resuming content playback in live mode on stop:\", error);\n          });\n        }\n      }\n      currentAd = void 0;\n      podAds = [];\n      podIndex = 0;\n    },\n    destroy() {\n      console.log(\"[HlsAdPlayer] Destroying\");\n      destroyed = true;\n      clearStallWatchdog();\n      for (const timeoutId of pendingTimeouts) {\n        clearTimeout(timeoutId);\n      }\n      pendingTimeouts = [];\n      adPlaying = false;\n      setAdPlayingFlag(false);\n      contentVideo.muted = originalMutedState;\n      contentVideo.volume = Math.max(0, Math.min(1, originalVolume));\n      releaseAdDecoder();\n      if (adContainerEl?.parentElement) {\n        adContainerEl.parentElement.removeChild(adContainerEl);\n      }\n      adContainerEl = void 0;\n      currentAd = void 0;\n      podAds = [];\n      podIndex = 0;\n      listeners.clear();\n      preloadedAds.clear();\n      preloadingAds.clear();\n    },\n    isAdPlaying() {\n      return adPlaying;\n    },\n    resize(width, height) {\n      console.log(`[HlsAdPlayer] Resizing to ${width}x${height}`);\n      if (adContainerEl) {\n        adContainerEl.style.width = `${width}px`;\n        adContainerEl.style.height = `${height}px`;\n      }\n      if (adVideoElement) {\n        adVideoElement.style.width = `${width}px`;\n        adVideoElement.style.height = `${height}px`;\n      }\n    },\n    on(event, listener) {\n      if (!listeners.has(event)) listeners.set(event, /* @__PURE__ */ new Set());\n      listeners.get(event).add(listener);\n    },\n    off(event, listener) {\n      listeners.get(event)?.delete(listener);\n    },\n    updateOriginalMutedState(muted, volume) {\n      const nextVolume = typeof volume === \"number\" && !Number.isNaN(volume) ? Math.max(0, Math.min(1, volume)) : originalVolume;\n      console.log(\n        `[HlsAdPlayer] updateOriginalMutedState called: { muted: ${originalMutedState} -> ${muted}, volume: ${originalVolume} -> ${nextVolume} }`\n      );\n      originalMutedState = muted;\n      originalVolume = nextVolume;\n    },\n    getOriginalMutedState() {\n      return originalMutedState;\n    },\n    getOriginalVolume() {\n      return originalVolume;\n    },\n    setAdVolume(volume) {\n      if (adVideoElement && adPlaying) {\n        const clamped = Math.max(0, Math.min(1, volume));\n        adVideoElement.volume = clamped;\n        adVideoElement.muted = clamped === 0;\n      }\n    },\n    getAdVolume() {\n      if (adVideoElement && adPlaying) {\n        return adVideoElement.volume;\n      }\n      return 1;\n    },\n    showPlaceholder() {\n      contentVideo.style.opacity = \"0\";\n      contentVideo.style.visibility = \"hidden\";\n      if (!adContainerEl) {\n        const container = document.createElement(\"div\");\n        container.style.position = \"absolute\";\n        container.style.left = \"0\";\n        container.style.top = \"0\";\n        container.style.right = \"0\";\n        container.style.bottom = \"0\";\n        container.style.display = \"none\";\n        container.style.alignItems = \"center\";\n        container.style.justifyContent = \"center\";\n        container.style.pointerEvents = \"none\";\n        container.style.zIndex = \"10\";\n        container.style.backgroundColor = \"#000\";\n        contentVideo.parentElement?.appendChild(container);\n        adContainerEl = container;\n      }\n      if (adContainerEl) {\n        adContainerEl.style.display = \"flex\";\n        adContainerEl.style.pointerEvents = \"auto\";\n      }\n    },\n    hidePlaceholder() {\n      if (adContainerEl) {\n        adContainerEl.style.display = \"none\";\n        adContainerEl.style.pointerEvents = \"none\";\n      }\n      if (!adPlaying) {\n        contentVideo.style.visibility = \"visible\";\n        contentVideo.style.opacity = \"1\";\n      }\n    },\n    getLoadedAdDuration() {\n      return currentAd?.duration;\n    },\n    getLoadedAdId() {\n      return currentAd?.id;\n    },\n    getPodAdCount() {\n      return podAds.length;\n    },\n    getPodTotalDurationMs() {\n      return podAds.reduce(\n        (total, ad) => total + (ad.duration > 0 ? ad.duration * 1e3 : 0),\n        0\n      );\n    }\n  };\n}\n\n// src/utils/devUrl.ts\nvar PRIVATE_HOST_PATTERNS = [\n  /^localhost$/i,\n  /^127\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^0\\.0\\.0\\.0$/,\n  /^::1$/,\n  /^10\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^192\\.168\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^172\\.(1[6-9]|2\\d|3[0-1])\\.\\d{1,3}\\.\\d{1,3}$/\n];\nfunction isLocalDevHost(hostname) {\n  const host = hostname.replace(/^\\[/, \"\").replace(/\\]$/, \"\").toLowerCase();\n  if (!host) return false;\n  if (host.endsWith(\".local\") || host.endsWith(\".localhost\")) return true;\n  return PRIVATE_HOST_PATTERNS.some((pattern) => pattern.test(host));\n}\nfunction toDevSafeUrl(rawUrl) {\n  if (!rawUrl) return rawUrl ?? \"\";\n  let url;\n  try {\n    url = new URL(rawUrl);\n  } catch {\n    return rawUrl;\n  }\n  if (url.protocol !== \"http:\" && url.protocol !== \"https:\") {\n    return rawUrl;\n  }\n  if (!isLocalDevHost(url.hostname)) {\n    return rawUrl;\n  }\n  const cleanPath = url.pathname.replace(/\\/{2,}/g, \"/\") || \"/index.html\";\n  return `file://${cleanPath}`;\n}\n\n// src/sdk/pal.ts\nvar PAL_SDK_URL = \"https://imasdk.googleapis.com/pal/sdkloader/pal.js\";\nvar _nonceLoader;\nvar _palLoadPromise;\nfunction loadPalSdk() {\n  if (typeof window !== \"undefined\" && window.goog?.pal) {\n    return Promise.resolve();\n  }\n  if (_palLoadPromise) return _palLoadPromise;\n  _palLoadPromise = new Promise((resolve, reject) => {\n    const existing = document.querySelector(\n      'script[data-pal=\"true\"]'\n    );\n    if (existing) {\n      if (window.goog?.pal) {\n        resolve();\n        return;\n      }\n      const timeout = setTimeout(\n        () => reject(new Error(\"PAL SDK load timeout\")),\n        1e4\n      );\n      existing.addEventListener(\"load\", () => {\n        clearTimeout(timeout);\n        resolve();\n      });\n      existing.addEventListener(\"error\", () => {\n        clearTimeout(timeout);\n        reject(new Error(\"PAL SDK load failed\"));\n      });\n      return;\n    }\n    const script = document.createElement(\"script\");\n    script.src = PAL_SDK_URL;\n    script.async = true;\n    script.setAttribute(\"data-pal\", \"true\");\n    script.onload = () => resolve();\n    script.onerror = () => reject(new Error(\"PAL SDK load failed\"));\n    document.head.appendChild(script);\n  });\n  return _palLoadPromise;\n}\nfunction getOrCreateNonceLoader() {\n  if (_nonceLoader) return _nonceLoader;\n  const goog = window.goog;\n  const consentSettings = new goog.pal.ConsentSettings();\n  consentSettings.allowStorage = true;\n  _nonceLoader = new goog.pal.NonceLoader(consentSettings);\n  return _nonceLoader;\n}\nfunction createPalNonceManager() {\n  let currentNonce = \"\";\n  let currentNonceManager;\n  return {\n    async generateNonce(options = {}) {\n      try {\n        await loadPalSdk();\n        const loader = getOrCreateNonceLoader();\n        const goog = window.goog;\n        const request = new goog.pal.NonceRequest();\n        request.adWillAutoPlay = options.adWillAutoPlay ?? true;\n        request.adWillPlayMuted = options.adWillPlayMuted ?? false;\n        request.playerVolume = options.playerVolume ?? (request.adWillPlayMuted ? 0 : 1);\n        request.continuousPlayback = options.continuousPlayback ?? true;\n        request.descriptionUrl = toDevSafeUrl(\n          options.descriptionUrl || (typeof window !== \"undefined\" ? window.location.href : \"\")\n        );\n        request.iconsSupported = true;\n        request.playerType = \"StormcloudVideoPlayer\";\n        request.playerVersion = \"1.0\";\n        request.supportedApiFrameworks = \"2,7,9\";\n        request.url = toDevSafeUrl(\n          options.descriptionUrl || (typeof window !== \"undefined\" ? window.location.href : \"\")\n        );\n        request.videoWidth = options.videoWidth || 640;\n        request.videoHeight = options.videoHeight || 480;\n        if (options.ppid) request.ppid = options.ppid;\n        if (options.sessionId) request.sessionId = options.sessionId;\n        console.log(\n          \"[PAL] NonceRequest before generateNonce:\",\n          JSON.stringify({\n            adWillAutoPlay: request.adWillAutoPlay,\n            adWillPlayMuted: request.adWillPlayMuted,\n            playerVolume: request.playerVolume,\n            continuousPlayback: request.continuousPlayback,\n            descriptionUrl: request.descriptionUrl,\n            iconsSupported: request.iconsSupported,\n            playerType: request.playerType,\n            playerVersion: request.playerVersion,\n            supportedApiFrameworks: request.supportedApiFrameworks,\n            url: request.url,\n            videoWidth: request.videoWidth,\n            videoHeight: request.videoHeight,\n            ppid: request.ppid,\n            sessionId: request.sessionId\n          }, null, 2)\n        );\n        const manager = await loader.loadNonceManager(request);\n        currentNonceManager = manager;\n        currentNonce = manager.getNonce();\n        console.log(\"[PAL] Nonce generated successfully\");\n        return currentNonce;\n      } catch (error) {\n        console.warn(\"[PAL] Failed to generate nonce:\", error);\n        currentNonce = \"\";\n        currentNonceManager = void 0;\n        return \"\";\n      }\n    },\n    getCurrentNonce() {\n      return currentNonce;\n    },\n    injectNonce(vastTagUrl) {\n      if (!currentNonce || !vastTagUrl) return vastTagUrl;\n      try {\n        const url = new URL(vastTagUrl);\n        url.searchParams.delete(\"paln\");\n        url.searchParams.set(\"givn\", currentNonce);\n        return url.toString();\n      } catch {\n        let base = vastTagUrl.replace(/([?&])paln=[^&]*/g, \"\").replace(/[?&]$/, \"\");\n        const sep = base.includes(\"?\") ? \"&\" : \"?\";\n        return `${base}${sep}givn=${encodeURIComponent(currentNonce)}`;\n      }\n    },\n    sendPlaybackStart() {\n      try {\n        currentNonceManager?.sendPlaybackStart();\n      } catch {\n      }\n    },\n    sendPlaybackEnd() {\n      try {\n        currentNonceManager?.sendPlaybackEnd();\n      } catch {\n      }\n    },\n    sendAdClick() {\n      try {\n        currentNonceManager?.sendAdClick();\n      } catch {\n      }\n    },\n    sendAdTouch(event) {\n      try {\n        currentNonceManager?.sendAdTouch(event);\n      } catch {\n      }\n    },\n    reset() {\n      currentNonce = \"\";\n      currentNonceManager = void 0;\n    }\n  };\n}\n\n// src/utils/mqttConfig.ts\nvar DEFAULT_MQTT_CONFIG = {\n  enabled: true,\n  brokerAddress: \"vecbae77.ala.us-east-1.emqxsl.com\",\n  brokerPort: 8883,\n  wsPort: 8084,\n  username: \"for-sonifi\",\n  password: \"sonifi-mqtt\",\n  topicPrefix: \"adstorm/players\",\n  qos: 1\n};\nvar mqttConfig = { ...DEFAULT_MQTT_CONFIG };\nfunction applyMQTTConfig(overrides) {\n  Object.assign(mqttConfig, overrides);\n}\nfunction isMQTTEnabled() {\n  return mqttConfig.enabled;\n}\nfunction buildMQTTBrokerUrl() {\n  if (mqttConfig.brokerUrl) return mqttConfig.brokerUrl;\n  return `wss://${mqttConfig.brokerAddress}:${mqttConfig.wsPort}/mqtt`;\n}\nfunction buildPlayerTopic(licenseKey, channel) {\n  return `${mqttConfig.topicPrefix}/${licenseKey}/${channel}`;\n}\n\n// src/utils/mqttClient.ts\nvar import_mqtt = __toESM(require(\"mqtt\"), 1);\nvar LOG = \"[StormcloudVideoPlayer][MQTT]\";\nvar KEEPALIVE_SECONDS = 30;\nvar CONNECT_TIMEOUT_MS = 1e4;\nvar RECONNECT_BASE_MS = 5e3;\nvar RECONNECT_MAX_MS = 6e4;\nvar MAX_RECONNECT_ATTEMPTS = 8;\nvar COOLDOWN_MS = 10 * 6e4;\nvar client = null;\nvar status = \"disconnected\";\nvar reconnectAttempts = 0;\nvar reconnectTimer = null;\nvar stopped = false;\nfunction clearReconnectTimer() {\n  if (reconnectTimer) {\n    clearTimeout(reconnectTimer);\n    reconnectTimer = null;\n  }\n}\nfunction teardownClient() {\n  if (client) {\n    try {\n      client.removeAllListeners();\n      client.end(true);\n    } catch {\n    }\n    client = null;\n  }\n}\nfunction scheduleReconnect() {\n  if (stopped || !isMQTTEnabled() || reconnectTimer) return;\n  if (reconnectAttempts >= MAX_RECONNECT_ATTEMPTS) {\n    console.warn(\n      `${LOG} giving up after ${reconnectAttempts} attempts; cooling down for ${COOLDOWN_MS / 6e4}m`\n    );\n    teardownClient();\n    status = \"disconnected\";\n    reconnectTimer = setTimeout(() => {\n      reconnectTimer = null;\n      reconnectAttempts = 0;\n      openConnection();\n    }, COOLDOWN_MS);\n    return;\n  }\n  const delay = Math.min(\n    RECONNECT_MAX_MS,\n    RECONNECT_BASE_MS * 2 ** reconnectAttempts\n  );\n  const jitter = Math.floor(Math.random() * 1e3);\n  reconnectAttempts += 1;\n  reconnectTimer = setTimeout(() => {\n    reconnectTimer = null;\n    openConnection();\n  }, delay + jitter);\n}\nfunction openConnection() {\n  if (stopped || !isMQTTEnabled()) return;\n  teardownClient();\n  const url = buildMQTTBrokerUrl();\n  status = \"connecting\";\n  const clientId = `stormcloud-vp-${Math.random().toString(36).slice(2, 9)}`;\n  try {\n    client = import_mqtt.default.connect(url, {\n      clientId,\n      username: mqttConfig.username,\n      password: mqttConfig.password,\n      keepalive: KEEPALIVE_SECONDS,\n      clean: true,\n      // Disable MQTT.js internal reconnect; we manage reconnection ourselves.\n      reconnectPeriod: 0,\n      connectTimeout: CONNECT_TIMEOUT_MS,\n      queueQoSZero: false,\n      reschedulePings: true,\n      // Root-cause fix for the Tizen 4.0 \"Keepalive timeout\" loop: MQTT.js's\n      // default timerVariant \"auto\" runs the keepalive interval inside a\n      // Blob-URL Web Worker (via worker-timers). On Samsung Tizen 4.0 (old\n      // WebKit) served from a file:// origin that worker can't tick reliably,\n      // so the keepalive counter trips onKeepaliveTimeout almost immediately\n      // after connect. Force the native setInterval timer instead; the main\n      // thread is free because video is decoded by the native AVPlay pipeline.\n      timerVariant: \"native\"\n    });\n  } catch (err) {\n    status = \"error\";\n    console.warn(`${LOG} connect() threw:`, err);\n    scheduleReconnect();\n    return;\n  }\n  client.on(\"connect\", () => {\n    status = \"connected\";\n    reconnectAttempts = 0;\n    clearReconnectTimer();\n    console.info(`${LOG} connected to ${url}`);\n  });\n  client.on(\"offline\", () => {\n    if (status === \"connected\") status = \"disconnected\";\n    console.warn(`${LOG} offline`);\n    scheduleReconnect();\n  });\n  client.on(\"error\", (err) => {\n    status = \"error\";\n    console.warn(`${LOG} error:`, err.message);\n    scheduleReconnect();\n  });\n  client.on(\"close\", () => {\n    if (status === \"connected\") status = \"disconnected\";\n    scheduleReconnect();\n  });\n}\nfunction initMQTTClient() {\n  if (client || !isMQTTEnabled()) return;\n  stopped = false;\n  reconnectAttempts = 0;\n  openConnection();\n}\nfunction ensureMQTTClient() {\n  if (isMQTTEnabled() && !client && !reconnectTimer) {\n    initMQTTClient();\n  }\n}\nfunction publishMQTT(topic, payload) {\n  if (!isMQTTEnabled()) {\n    return false;\n  }\n  ensureMQTTClient();\n  if (!client || !client.connected) {\n    return false;\n  }\n  try {\n    client.publish(topic, JSON.stringify(payload), { qos: mqttConfig.qos });\n    return true;\n  } catch (err) {\n    console.warn(`${LOG} publish failed on ${topic}:`, err);\n    return false;\n  }\n}\n\n// src/utils/vastEnvironmentSignals.ts\nvar AIRY_ANDROID_APP_ID = \"com.freeairytv.android\";\nvar AIRY_WEBOS_APP_ID = \"com.freeairytv.webos\";\nvar AIRY_TIZEN_APP_ID = \"com.freeairytv.samsung\";\nvar AIRY_ROKU_APP_ID = \"com.freeairytv.roku\";\nvar AIRY_APP_NAME = \"AiryTV Movies & TV\";\nvar AIRY_DEFAULT_CONTENT_URL = \"https://live.airy.tv\";\nvar CTV_SESSION_STORAGE_KEY = \"stormcloud.ctv.sid\";\nvar PLAYER_ID_STORAGE_KEY = \"stormcloud.player.id\";\nvar LG_TEST_APP_ID = \"com.hulu.plus\";\nvar LG_TEST_APP_NAME = \"Hulu\";\nvar LG_TEST_CONTENT_URL = \"https://www.hulu.com/live-tv\";\nvar _lgTestDeviceId;\nfunction getLgTestDeviceId() {\n  if (!_lgTestDeviceId) _lgTestDeviceId = createUuid();\n  return _lgTestDeviceId;\n}\nfunction isLgWebOS() {\n  if (typeof navigator === \"undefined\") return false;\n  return /Web0S|webOS|LG Browser|LGSTB|LGE/i.test(navigator.userAgent);\n}\nfunction getDefaultAppId() {\n  if (typeof navigator === \"undefined\") return AIRY_ANDROID_APP_ID;\n  const ua = navigator.userAgent;\n  if (/Web0S|webOS|LG Browser|LGSTB|LGE/i.test(ua)) return AIRY_WEBOS_APP_ID;\n  if (/Tizen|Samsung/i.test(ua)) return AIRY_TIZEN_APP_ID;\n  if (/Roku/i.test(ua)) return AIRY_ROKU_APP_ID;\n  return AIRY_ANDROID_APP_ID;\n}\nvar DEVICE_ID_STORAGE_KEYS = [\n  \"rdid\",\n  \"ifa\",\n  \"advertisingId\",\n  \"advertising_id\",\n  \"deviceAdvertisingId\",\n  \"aaid\",\n  \"adid\",\n  \"rida\",\n  \"tifa\",\n  \"lgudid\"\n];\nvar ANDROID_ID_TYPES = /* @__PURE__ */ new Set([\"aaid\", \"adid\"]);\nfunction resolveVastEnvironmentSignals(isCtv) {\n  const bridgeSignals = readNativeBridgeSignals();\n  const platformDevice = readPlatformNativeDeviceId();\n  const lg = isCtv && isLgWebOS();\n  const deviceId = bridgeSignals.deviceId || readStoredDeviceId() || platformDevice.deviceId || (lg && platformDevice.limitAdTracking !== true ? getLgTestDeviceId() : void 0);\n  const deviceIdType = bridgeSignals.deviceIdType || readStoredString(\"deviceIdType\") || readStoredString(\"idtype\") || platformDevice.deviceIdType || inferDeviceIdType() || (lg ? \"lgudid\" : void 0);\n  const platformLat = bridgeSignals.deviceId ? bridgeSignals.limitAdTracking : platformDevice.limitAdTracking;\n  const limitAdTracking = deviceId != null ? platformLat ?? readStoredLimitAdTracking() ?? false : void 0;\n  if (isCtv) {\n    return {\n      isCtv: true,\n      contentUrl: bridgeSignals.contentUrl || readStoredString(\"contentUrl\") || (lg ? LG_TEST_CONTENT_URL : AIRY_DEFAULT_CONTENT_URL),\n      appId: bridgeSignals.appId || readStoredString(\"appId\") || readStoredString(\"msid\") || (lg ? LG_TEST_APP_ID : getDefaultAppId()),\n      appName: bridgeSignals.appName || readStoredString(\"appName\") || readStoredString(\"an\") || (lg ? LG_TEST_APP_NAME : AIRY_APP_NAME),\n      sessionId: getOrCreateCtvSessionId(),\n      ...deviceId ? { deviceId } : {},\n      ...deviceIdType ? { deviceIdType } : {},\n      ...limitAdTracking != null ? { limitAdTracking } : {},\n      deviceTypeHint: 5\n    };\n  }\n  return {\n    isCtv: false,\n    ...deviceId ? { deviceId } : {},\n    ...deviceIdType ? { deviceIdType } : {},\n    ...limitAdTracking != null ? { limitAdTracking } : {}\n  };\n}\nfunction inferDeviceIdType() {\n  if (typeof navigator === \"undefined\") {\n    return void 0;\n  }\n  const ua = navigator.userAgent;\n  if (/Roku/i.test(ua)) return \"rida\";\n  if (/Tizen|Samsung/i.test(ua)) return \"tifa\";\n  if (/AppleTV|Apple TV/i.test(ua)) return \"tvOS\";\n  if (/AFT|Fire TV|Amazon/i.test(ua)) return \"afai\";\n  if (/Web0S|webOS|LG Browser|LGSTB|LGE/i.test(ua)) return \"lgudid\";\n  if (/Android|Google TV/i.test(ua)) return \"aaid\";\n  if (/iPhone|iPad|iPod/i.test(ua)) return \"idfa\";\n  return void 0;\n}\nfunction isEquivalentDeviceIdType(tagType, runtimeType) {\n  if (!tagType || !runtimeType) return false;\n  const tag = tagType.toLowerCase();\n  const runtime = runtimeType.toLowerCase();\n  if (tag === runtime) return true;\n  return ANDROID_ID_TYPES.has(tag) && ANDROID_ID_TYPES.has(runtime);\n}\nfunction resolveNativeDeviceId() {\n  const bridgeSignals = readNativeBridgeSignals();\n  const platformDevice = readPlatformNativeDeviceId();\n  const deviceId = bridgeSignals.deviceId || readStoredDeviceId() || platformDevice.deviceId;\n  if (!deviceId || isMacroPlaceholder(deviceId) || isZeroedAdId(deviceId)) {\n    return void 0;\n  }\n  return deviceId;\n}\nfunction getOrCreateStoredUuid(storageKey) {\n  if (typeof window === \"undefined\") {\n    return void 0;\n  }\n  const existing = readPersistentId(storageKey);\n  if (existing) {\n    writePersistentId(storageKey, existing);\n    return existing;\n  }\n  const id = createUuid();\n  writePersistentId(storageKey, id);\n  return id;\n}\nfunction getOrCreateCtvSessionId() {\n  const existing = readPersistentId(CTV_SESSION_STORAGE_KEY);\n  if (existing) {\n    writePersistentId(CTV_SESSION_STORAGE_KEY, existing);\n    return existing;\n  }\n  const sessionId = createUuid();\n  writePersistentId(CTV_SESSION_STORAGE_KEY, sessionId);\n  return sessionId;\n}\nfunction readPersistentId(storageKey) {\n  return readStoredString(storageKey) || readCookie(storageKey);\n}\nfunction writePersistentId(storageKey, value) {\n  try {\n    window.localStorage?.setItem(storageKey, value);\n  } catch {\n  }\n  writeCookie(storageKey, value);\n}\nvar PERSISTENT_ID_COOKIE_MAX_AGE = 60 * 60 * 24 * 365 * 5;\nfunction readCookie(name) {\n  if (typeof document === \"undefined\") {\n    return void 0;\n  }\n  try {\n    const prefix = encodeURIComponent(name) + \"=\";\n    const parts = document.cookie ? document.cookie.split(\";\") : [];\n    for (const part of parts) {\n      const entry = part.trim();\n      if (entry.startsWith(prefix)) {\n        return decodeURIComponent(entry.slice(prefix.length)) || void 0;\n      }\n    }\n  } catch {\n  }\n  return void 0;\n}\nfunction writeCookie(name, value) {\n  if (typeof document === \"undefined\") {\n    return;\n  }\n  try {\n    document.cookie = encodeURIComponent(name) + \"=\" + encodeURIComponent(value) + \";path=/;max-age=\" + PERSISTENT_ID_COOKIE_MAX_AGE + \";SameSite=Lax\";\n  } catch {\n  }\n}\nfunction createUuid() {\n  if (typeof crypto !== \"undefined\" && typeof crypto.randomUUID === \"function\") {\n    return crypto.randomUUID();\n  }\n  const bytes = new Uint8Array(16);\n  if (typeof crypto !== \"undefined\" && typeof crypto.getRandomValues === \"function\") {\n    crypto.getRandomValues(bytes);\n  } else {\n    let seed = Date.now() ^ Math.floor(performanceNow() * 1e3);\n    for (let i = 0; i < 16; i++) {\n      seed = seed * 1103515245 + 12345 & 2147483647;\n      bytes[i] = (seed ^ Math.floor(Math.random() * 256)) & 255;\n    }\n  }\n  bytes[6] = (bytes[6] ?? 0) & 15 | 64;\n  bytes[8] = (bytes[8] ?? 0) & 63 | 128;\n  let hex = \"\";\n  for (let i = 0; i < 16; i++) {\n    hex += (bytes[i] ?? 0).toString(16).padStart(2, \"0\");\n  }\n  return hex.slice(0, 8) + \"-\" + hex.slice(8, 12) + \"-\" + hex.slice(12, 16) + \"-\" + hex.slice(16, 20) + \"-\" + hex.slice(20, 32);\n}\nfunction performanceNow() {\n  try {\n    if (typeof performance !== \"undefined\" && typeof performance.now === \"function\") {\n      return performance.now();\n    }\n  } catch {\n  }\n  return 0;\n}\nfunction readPlatformNativeDeviceId() {\n  if (typeof window === \"undefined\") return {};\n  try {\n    const adinfo = window.webapis?.adinfo;\n    if (adinfo) {\n      const tifa = typeof adinfo.getTIFA === \"function\" ? adinfo.getTIFA() : adinfo.tifa;\n      if (typeof tifa === \"string\" && tifa && !isMacroPlaceholder(tifa)) {\n        const lat = typeof adinfo.isLATEnabled === \"function\" ? adinfo.isLATEnabled() : void 0;\n        return {\n          deviceId: tifa,\n          deviceIdType: \"tifa\",\n          ...typeof lat === \"boolean\" ? { limitAdTracking: lat } : {}\n        };\n      }\n    }\n  } catch {\n  }\n  try {\n    const webOSDev = window.webOSDev;\n    if (webOSDev) {\n      const lgudid = typeof webOSDev.LGUDID === \"function\" ? webOSDev.LGUDID() : webOSDev.lgudid ?? webOSDev.LGUDID;\n      if (typeof lgudid === \"string\" && lgudid) {\n        if (isZeroedAdId(lgudid)) {\n          return { deviceIdType: \"lgudid\", limitAdTracking: true };\n        }\n        if (!isMacroPlaceholder(lgudid)) {\n          return { deviceId: lgudid, deviceIdType: \"lgudid\", limitAdTracking: false };\n        }\n      }\n    }\n  } catch {\n  }\n  try {\n    const roku = window.Roku;\n    if (roku) {\n      const rida = typeof roku.getPublisherUniqueId === \"function\" ? roku.getPublisherUniqueId() : roku.rida;\n      if (typeof rida === \"string\" && rida && !isMacroPlaceholder(rida)) {\n        return { deviceId: rida, deviceIdType: \"rida\", limitAdTracking: false };\n      }\n    }\n  } catch {\n  }\n  return {};\n}\nvar ZEROED_AD_ID_PATTERNS = /* @__PURE__ */ new Set([\n  \"38400000-8cf0-11bd-b23e-10b96e40000d\",\n  \"00000000-0000-0000-0000-000000000000\"\n]);\nfunction isMacroPlaceholder(value) {\n  const t = value.trim();\n  return !t || /^(\\[[^\\]]*\\]|\\{[^}]*\\}|%%[^%]*%%)$/.test(t) || /^(unknown|null|undefined|none|n\\/a|\\$\\{[^}]+\\})$/i.test(t) || ZEROED_AD_ID_PATTERNS.has(t.toLowerCase());\n}\nfunction isZeroedAdId(value) {\n  return ZEROED_AD_ID_PATTERNS.has(value.trim().toLowerCase());\n}\nfunction readNativeBridgeSignals() {\n  if (typeof window === \"undefined\") {\n    return {};\n  }\n  const candidates = [\n    window.__STORMCLOUD_CTV_AD_INFO__,\n    window.__STORMCLOUD_CTV__,\n    window.stormcloudCtv,\n    window.AiryTV,\n    window.Android,\n    window.webOS,\n    window.tizen,\n    window.amazon\n  ].filter(Boolean);\n  for (const source of candidates) {\n    const contentUrl = readBridgeValue(source, [\"contentUrl\", \"url\", \"videoUrl\", \"canonicalUrl\"]) || void 0;\n    const appId = readBridgeValue(source, [\"appId\", \"msid\", \"applicationId\", \"packageName\"]) || void 0;\n    const appName = readBridgeValue(source, [\"appName\", \"an\", \"applicationName\"]) || void 0;\n    const deviceId = readBridgeValue(source, [\n      \"rdid\",\n      \"ifa\",\n      \"advertisingId\",\n      \"adId\",\n      \"deviceId\",\n      \"lgudid\",\n      \"LGUDID\",\n      \"tifa\",\n      \"rida\",\n      \"afai\",\n      \"aaid\"\n    ]) || void 0;\n    if (!contentUrl && !deviceId && !appId && !appName) continue;\n    const deviceIdType = readBridgeValue(source, [\n      \"idtype\",\n      \"deviceIdType\",\n      \"advertisingIdType\",\n      \"idType\"\n    ]) || inferDeviceIdType();\n    const limitAdTracking = readBridgeBoolean(source, [\n      \"is_lat\",\n      \"limitAdTracking\",\n      \"limitedAdTracking\",\n      \"lat\"\n    ]);\n    return {\n      ...contentUrl ? { contentUrl } : {},\n      ...appId ? { appId } : {},\n      ...appName ? { appName } : {},\n      ...deviceId ? { deviceId } : {},\n      ...deviceId && deviceIdType ? { deviceIdType } : {},\n      ...deviceId && limitAdTracking != null ? { limitAdTracking } : {}\n    };\n  }\n  return {};\n}\nfunction readBridgeValue(source, keys) {\n  for (const key of keys) {\n    const value = source?.[key];\n    if (typeof value === \"string\" && value) {\n      return value;\n    }\n    if (typeof value === \"function\") {\n      try {\n        const result = value.call(source);\n        if (typeof result === \"string\" && result) {\n          return result;\n        }\n      } catch {\n      }\n    }\n  }\n  return void 0;\n}\nfunction readBridgeBoolean(source, keys) {\n  for (const key of keys) {\n    const value = source?.[key];\n    const normalized = normalizeBoolean(value);\n    if (normalized != null) {\n      return normalized;\n    }\n    if (typeof value === \"function\") {\n      try {\n        const result = normalizeBoolean(value.call(source));\n        if (result != null) {\n          return result;\n        }\n      } catch {\n      }\n    }\n  }\n  return void 0;\n}\nfunction readStoredDeviceId() {\n  for (const key of DEVICE_ID_STORAGE_KEYS) {\n    const value = readStoredString(key);\n    if (value) {\n      return value;\n    }\n  }\n  return void 0;\n}\nfunction readStoredString(key) {\n  if (typeof window === \"undefined\") {\n    return void 0;\n  }\n  try {\n    const value = window.localStorage?.getItem(key);\n    return value || void 0;\n  } catch {\n    return void 0;\n  }\n}\nfunction readStoredLimitAdTracking() {\n  return normalizeBoolean(\n    readStoredString(\"limitAdTracking\") || readStoredString(\"limitedAdTracking\") || readStoredString(\"is_lat\")\n  );\n}\nfunction normalizeBoolean(value) {\n  if (typeof value === \"boolean\") {\n    return value;\n  }\n  if (typeof value === \"number\") {\n    return value === 1;\n  }\n  if (typeof value === \"string\") {\n    const normalized = value.toLowerCase();\n    if (normalized === \"1\" || normalized === \"true\" || normalized === \"yes\") {\n      return true;\n    }\n    if (normalized === \"0\" || normalized === \"false\" || normalized === \"no\") {\n      return false;\n    }\n  }\n  return void 0;\n}\n\n// src/utils/tracking.ts\nvar cachedBrowserId = null;\nfunction buildAnalyticsContext(config) {\n  const context = {};\n  if (config.debugAdTiming) {\n    context.debugAdTiming = true;\n  }\n  if (config.isLiveStream !== void 0) {\n    context.inputStreamType = config.isLiveStream ? \"live\" : \"vod\";\n  }\n  return context;\n}\nfunction getClientInfo() {\n  const ua = navigator.userAgent;\n  const platform = navigator.platform;\n  const vendor = navigator.vendor || \"\";\n  const maxTouchPoints = navigator.maxTouchPoints || 0;\n  const memory = navigator.deviceMemory || null;\n  const hardwareConcurrency = navigator.hardwareConcurrency || 1;\n  const screenInfo = {\n    width: screen?.width,\n    height: screen?.height,\n    availWidth: screen?.availWidth,\n    availHeight: screen?.availHeight,\n    orientation: screen?.orientation?.type || \"\",\n    pixelDepth: screen?.pixelDepth\n  };\n  let deviceType = \"desktop\";\n  let brand = \"Unknown\";\n  let os = \"Unknown\";\n  let model = \"\";\n  let isSmartTV = false;\n  let isAndroid = false;\n  let isWebView = false;\n  let isWebApp = false;\n  if (ua.includes(\"Web0S\")) {\n    brand = \"LG\";\n    os = \"webOS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n    const webosMatch = ua.match(/Web0S\\/([^\\s]+)/);\n    model = webosMatch ? `webOS ${webosMatch[1]}` : \"webOS TV\";\n  } else if (ua.includes(\"Tizen\")) {\n    brand = \"Samsung\";\n    os = \"Tizen\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n    const tizenMatch = ua.match(/Tizen\\/([^\\s]+)/);\n    const tvMatch = ua.match(/(?:Smart-TV|SMART-TV|TV)/i) ? \"Smart TV\" : \"\";\n    model = tizenMatch ? `Tizen ${tizenMatch[1]} ${tvMatch}`.trim() : \"Tizen TV\";\n  } else if (ua.includes(\"Philips\")) {\n    brand = \"Philips\";\n    os = \"Saphi\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"Sharp\") || ua.includes(\"AQUOS\")) {\n    brand = \"Sharp\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"Android\") && (ua.includes(\"Sony\") || vendor.includes(\"Sony\"))) {\n    brand = \"Sony\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"Android\") && (ua.includes(\"NetCast\") || ua.includes(\"LG\"))) {\n    brand = \"LG\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\" Roku\") || ua.includes(\"Roku/\")) {\n    brand = \"Roku\";\n    os = \"Roku OS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"AppleTV\")) {\n    brand = \"Apple\";\n    os = \"tvOS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  }\n  if (ua.includes(\"Android\")) {\n    isAndroid = true;\n    os = \"Android\";\n    deviceType = /Mobile/.test(ua) ? \"mobile\" : \"tablet\";\n    if (ua.includes(\"Android\") && (maxTouchPoints === 0 || ua.includes(\"Google TV\") || ua.includes(\"XiaoMi\"))) {\n      deviceType = \"tv\";\n      isSmartTV = true;\n      brand = brand === \"Unknown\" ? \"Android TV\" : brand;\n    }\n    const androidModelMatch = ua.match(/\\(([^)]*Android[^)]*)\\)/);\n    if (androidModelMatch && androidModelMatch[1]) {\n      model = androidModelMatch[1];\n    }\n  }\n  if (/iPad|iPhone|iPod/.test(ua)) {\n    os = \"iOS\";\n    deviceType = \"mobile\";\n    brand = \"Apple\";\n    if (navigator.maxTouchPoints > 1 && /iPad/.test(ua)) {\n      deviceType = \"tablet\";\n    }\n  }\n  if (!isAndroid && !isSmartTV && !/Mobile/.test(ua)) {\n    if (ua.includes(\"Windows\")) {\n      os = \"Windows\";\n      deviceType = \"desktop\";\n    } else if (ua.includes(\"Mac\") && !/iPhone/.test(ua)) {\n      os = \"macOS\";\n      deviceType = \"desktop\";\n      if (maxTouchPoints > 1) deviceType = \"tablet\";\n    } else if (ua.includes(\"Linux\")) {\n      os = \"Linux\";\n      deviceType = \"desktop\";\n    }\n  }\n  if (brand === \"Unknown\") {\n    if (vendor.includes(\"Google\") || ua.includes(\"Chrome\")) brand = \"Google\";\n    if (vendor.includes(\"Apple\")) brand = \"Apple\";\n    if (vendor.includes(\"Samsung\") || ua.includes(\"SM-\")) brand = \"Samsung\";\n  }\n  isWebView = /wv|WebView|Linux; U;/.test(ua);\n  if (window?.outerHeight === 0 && window?.outerWidth === 0) {\n    isWebView = true;\n  }\n  isWebApp = window.matchMedia(\"(display-mode: standalone)\").matches || window.navigator.standalone === true || window.screen?.orientation?.angle !== void 0;\n  return {\n    brand,\n    os,\n    model: model || ua.substring(0, 50) + \"...\",\n    deviceType,\n    isSmartTV,\n    isAndroid,\n    isWebView,\n    isWebApp,\n    domain: window.location.hostname,\n    origin: window.location.origin,\n    path: window.location.pathname,\n    userAgent: ua,\n    vendor,\n    platform,\n    screen: screenInfo,\n    hardwareConcurrency,\n    deviceMemory: memory,\n    maxTouchPoints,\n    language: navigator.language,\n    languages: navigator.languages?.join(\",\") || \"\",\n    cookieEnabled: navigator.cookieEnabled,\n    doNotTrack: navigator.doNotTrack || \"\",\n    referrer: document.referrer,\n    visibilityState: document.visibilityState\n  };\n}\nasync function sha256Hex(input) {\n  if (typeof crypto !== \"undefined\" && crypto.subtle?.digest) {\n    try {\n      await crypto.subtle.digest(\"SHA-256\", new Uint8Array([1, 2, 3]));\n      let encodedData;\n      if (typeof TextEncoder !== \"undefined\") {\n        encodedData = new TextEncoder().encode(input);\n      } else {\n        const utf8 = unescape(encodeURIComponent(input));\n        const buffer = new Uint8Array(utf8.length);\n        for (let i = 0; i < utf8.length; i++) {\n          buffer[i] = utf8.charCodeAt(i);\n        }\n        encodedData = buffer;\n      }\n      const hashBuffer = await crypto.subtle.digest(\"SHA-256\", encodedData);\n      return Array.from(new Uint8Array(hashBuffer)).map((b) => b.toString(16).padStart(2, \"0\")).join(\"\");\n    } catch {\n      console.warn(\n        \"[StormcloudVideoPlayer] crypto.subtle not supported, using fallback hash\"\n      );\n    }\n  }\n  let hash = 0;\n  for (let i = 0; i < input.length; i++) {\n    const char = input.charCodeAt(i);\n    hash = (hash << 5) - hash + char;\n    hash = hash & hash;\n  }\n  const fallbackHash = Math.abs(hash).toString(16).padStart(8, \"0\");\n  const timestamp = Date.now().toString(16).padStart(12, \"0\");\n  const random = Math.random().toString(16).substring(2, 14).padStart(12, \"0\");\n  return (fallbackHash + timestamp + random).padEnd(64, \"0\");\n}\nfunction resolvePlayerIdentitySeed(clientInfo) {\n  const nativeDeviceId = resolveNativeDeviceId();\n  if (nativeDeviceId) {\n    return `device:${nativeDeviceId}`;\n  }\n  const persistedId = getOrCreateStoredUuid(PLAYER_ID_STORAGE_KEY);\n  if (persistedId) {\n    return `persisted:${persistedId}`;\n  }\n  return `fingerprint:${JSON.stringify(clientInfo)}`;\n}\nasync function getBrowserID(clientInfo) {\n  if (cachedBrowserId) {\n    return cachedBrowserId;\n  }\n  cachedBrowserId = await sha256Hex(resolvePlayerIdentitySeed(clientInfo));\n  return cachedBrowserId;\n}\nfunction canPublish(licenseKey) {\n  return Boolean(isMQTTEnabled() && licenseKey);\n}\nasync function buildPlayerMetricEvent(context = {}, flags = {}) {\n  const clientInfo = getClientInfo();\n  const debugAdTiming = !!context.debugAdTiming;\n  if (debugAdTiming) {\n    console.log(\"[StormcloudVideoPlayer] clientInfo: \", JSON.stringify(clientInfo, null, 2));\n  }\n  const playerId = await getBrowserID(clientInfo);\n  if (debugAdTiming) {\n    console.log(\"[StormcloudVideoPlayer] playerId: \", playerId);\n  }\n  const captureAt = flags.captureAt ?? (/* @__PURE__ */ new Date()).toISOString();\n  return {\n    player_id: playerId,\n    device_type: clientInfo.deviceType,\n    os: clientInfo.os.toLowerCase(),\n    ad_loaded: flags.adLoaded ?? false,\n    ad_detect: flags.adDetect ?? false,\n    capture_at: captureAt,\n    ...context.inputStreamType ? { input_stream_type: context.inputStreamType } : {}\n  };\n}\nfunction publishTracking(licenseKey, channel, body) {\n  ensureMQTTClient();\n  publishMQTT(buildPlayerTopic(licenseKey, channel), body);\n}\nasync function sendInitialTracking(licenseKey, context = {}) {\n  if (!canPublish(licenseKey)) return;\n  try {\n    const metricEvent = await buildPlayerMetricEvent(context, {\n      adLoaded: false,\n      adDetect: false\n    });\n    publishTracking(licenseKey, \"metrics\", {\n      events: [metricEvent]\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending initial tracking data:\",\n      error\n    );\n  }\n}\nasync function sendAdDetectTracking(licenseKey, adDetectInfo, context = {}) {\n  try {\n    await sendHeartbeat(licenseKey, context, {\n      adDetect: true,\n      captureAt: adDetectInfo.timestamp\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad detect tracking:\",\n      error\n    );\n  }\n}\nasync function sendAdLoadedTracking(licenseKey, adLoadedInfo, context = {}) {\n  try {\n    await sendHeartbeat(licenseKey, context, {\n      adLoaded: true,\n      captureAt: adLoadedInfo.timestamp\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad loaded tracking:\",\n      error\n    );\n  }\n}\nasync function sendAdImpressionTracking(licenseKey, adImpressionInfo, context = {}) {\n  if (!canPublish(licenseKey)) return;\n  try {\n    const metricEvent = await buildPlayerMetricEvent(context, {\n      captureAt: adImpressionInfo.timestamp\n    });\n    publishTracking(licenseKey, \"heartbeat\", metricEvent);\n    publishTracking(licenseKey, \"impressions\", {\n      events: [\n        {\n          player_id: metricEvent.player_id,\n          ad_played_count: 1,\n          ad_url: adImpressionInfo.adUrl,\n          capture_at: adImpressionInfo.timestamp\n        }\n      ]\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad impression tracking:\",\n      error\n    );\n  }\n}\nasync function sendHeartbeat(licenseKey, context = {}, flags = {}) {\n  if (!canPublish(licenseKey)) return;\n  try {\n    const heartbeatData = await buildPlayerMetricEvent(context, flags);\n    publishTracking(licenseKey, \"heartbeat\", heartbeatData);\n  } catch (error) {\n    console.error(\"[StormcloudVideoPlayer] Error sending heartbeat:\", error);\n  }\n}\n\n// src/utils/polyfills.ts\nfunction polyfillURLSearchParams() {\n  if (typeof URLSearchParams !== \"undefined\") {\n    return;\n  }\n  class URLSearchParamsPolyfill {\n    constructor(init) {\n      this.params = /* @__PURE__ */ new Map();\n      if (typeof init === \"string\") {\n        this.parseQueryString(init);\n      } else if (init instanceof URLSearchParamsPolyfill) {\n        init.forEach((value, key) => {\n          this.append(key, value);\n        });\n      }\n    }\n    parseQueryString(query) {\n      const cleanQuery = query.startsWith(\"?\") ? query.slice(1) : query;\n      if (!cleanQuery) return;\n      cleanQuery.split(\"&\").forEach((param) => {\n        const [key, value] = param.split(\"=\");\n        if (key) {\n          const decodedKey = this.safeDecodeURIComponent(key);\n          const decodedValue = value ? this.safeDecodeURIComponent(value) : \"\";\n          this.append(decodedKey, decodedValue);\n        }\n      });\n    }\n    safeDecodeURIComponent(str) {\n      try {\n        return decodeURIComponent(str.replace(/\\+/g, \" \"));\n      } catch (e) {\n        return str;\n      }\n    }\n    append(name, value) {\n      const values = this.params.get(name) || [];\n      values.push(String(value));\n      this.params.set(name, values);\n    }\n    delete(name) {\n      this.params.delete(name);\n    }\n    get(name) {\n      const values = this.params.get(name);\n      return values && values.length > 0 && values[0] !== void 0 ? values[0] : null;\n    }\n    getAll(name) {\n      return this.params.get(name) || [];\n    }\n    has(name) {\n      return this.params.has(name);\n    }\n    set(name, value) {\n      this.params.set(name, [String(value)]);\n    }\n    forEach(callback) {\n      this.params.forEach((values, key) => {\n        values.forEach((value) => {\n          callback(value, key, this);\n        });\n      });\n    }\n    toString() {\n      const parts = [];\n      this.params.forEach((values, key) => {\n        values.forEach((value) => {\n          parts.push(`${encodeURIComponent(key)}=${encodeURIComponent(value)}`);\n        });\n      });\n      return parts.join(\"&\");\n    }\n  }\n  window.URLSearchParams = URLSearchParamsPolyfill;\n}\nfunction polyfillTextEncoder() {\n  if (typeof TextEncoder !== \"undefined\") {\n    return;\n  }\n  class TextEncoderPolyfill {\n    constructor() {\n      this.encoding = \"utf-8\";\n    }\n    encode(str) {\n      const utf8 = [];\n      for (let i = 0; i < str.length; i++) {\n        let charcode = str.charCodeAt(i);\n        if (charcode < 128) {\n          utf8.push(charcode);\n        } else if (charcode < 2048) {\n          utf8.push(192 | charcode >> 6, 128 | charcode & 63);\n        } else if (charcode < 55296 || charcode >= 57344) {\n          utf8.push(\n            224 | charcode >> 12,\n            128 | charcode >> 6 & 63,\n            128 | charcode & 63\n          );\n        } else {\n          i++;\n          charcode = 65536 + ((charcode & 1023) << 10 | str.charCodeAt(i) & 1023);\n          utf8.push(\n            240 | charcode >> 18,\n            128 | charcode >> 12 & 63,\n            128 | charcode >> 6 & 63,\n            128 | charcode & 63\n          );\n        }\n      }\n      return new Uint8Array(utf8);\n    }\n  }\n  window.TextEncoder = TextEncoderPolyfill;\n}\nfunction polyfillPromiseFinally() {\n  if (typeof Promise !== \"undefined\" && !Promise.prototype.finally) {\n    Promise.prototype.finally = function(callback) {\n      const constructor = this.constructor;\n      return this.then(\n        (value) => constructor.resolve(callback()).then(() => value),\n        (reason) => constructor.resolve(callback()).then(() => {\n          throw reason;\n        })\n      );\n    };\n  }\n}\nfunction polyfillObjectAssign() {\n  if (typeof Object.assign !== \"function\") {\n    Object.assign = function(target, ...sources) {\n      if (target == null) {\n        throw new TypeError(\"Cannot convert undefined or null to object\");\n      }\n      const to = Object(target);\n      for (let i = 0; i < sources.length; i++) {\n        const nextSource = sources[i];\n        if (nextSource != null) {\n          for (const nextKey in nextSource) {\n            if (Object.prototype.hasOwnProperty.call(nextSource, nextKey)) {\n              to[nextKey] = nextSource[nextKey];\n            }\n          }\n        }\n      }\n      return to;\n    };\n  }\n}\nfunction polyfillArrayFrom() {\n  if (!Array.from) {\n    Array.from = function(arrayLike, mapFn, thisArg) {\n      const items = Object(arrayLike);\n      if (arrayLike == null) {\n        throw new TypeError(\"Array.from requires an array-like object\");\n      }\n      const len = items.length >>> 0;\n      const result = new Array(len);\n      for (let i = 0; i < len; i++) {\n        if (mapFn) {\n          result[i] = mapFn.call(thisArg, items[i], i);\n        } else {\n          result[i] = items[i];\n        }\n      }\n      return result;\n    };\n  }\n}\nfunction polyfillStringStartsWith() {\n  if (!String.prototype.startsWith) {\n    String.prototype.startsWith = function(search, pos) {\n      pos = !pos || pos < 0 ? 0 : +pos;\n      return this.substring(pos, pos + search.length) === search;\n    };\n  }\n}\nfunction polyfillStringEndsWith() {\n  if (!String.prototype.endsWith) {\n    String.prototype.endsWith = function(search, length) {\n      if (length === void 0 || length > this.length) {\n        length = this.length;\n      }\n      return this.substring(length - search.length, length) === search;\n    };\n  }\n}\nfunction polyfillStringIncludes() {\n  if (!String.prototype.includes) {\n    String.prototype.includes = function(search, start) {\n      if (typeof start !== \"number\") {\n        start = 0;\n      }\n      if (start + search.length > this.length) {\n        return false;\n      }\n      return this.indexOf(search, start) !== -1;\n    };\n  }\n}\nfunction initializePolyfills() {\n  polyfillObjectAssign();\n  polyfillArrayFrom();\n  polyfillStringStartsWith();\n  polyfillStringEndsWith();\n  polyfillStringIncludes();\n  polyfillURLSearchParams();\n  polyfillTextEncoder();\n  polyfillPromiseFinally();\n}\n\n// src/utils/vastMacros.ts\nvar UNEXPANDED_MACRO_PATTERN = /^(\\[[^\\]]*\\]|\\{[^}]*\\}|%%[^%]*%%)$/;\nvar INVALID_VAST_PARAM_KEY = /^\\s|\\s$/;\nvar EXAMPLE_COM_URL = /example\\.com/i;\nvar CTV_UNSUPPORTED_PARAMS = [\n  \"description_url\",\n  \"tfcd\",\n  \"npa\",\n  \"min_ad_duration\",\n  \"max_ad_duration\",\n  \"unviewed_position_start\",\n  \"impl\",\n  \"vad_type\",\n  \"gdpr\",\n  \"gdpr_consent\",\n  \"us_privacy\"\n];\nvar INLINE_DEVICE_MACRO_REPLACEMENTS = [\n  { pattern: /\\[RDID\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[IFA\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[ADVERTISING[_-]?ID(?:ENTIFIER)?\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[DEVICE[_-]?ID\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[IDTYPE\\]/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /\\{rdid\\}/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\{device[_-]?id\\}/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\{idtype\\}/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /%%ADVERTISING_IDENTIFIER_PLAIN%%/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /%%ADVERTISING_ID_OPT_OUT%%/gi, getValue: (ctx) => ctx.limitAdTracking != null ? ctx.limitAdTracking ? \"1\" : \"0\" : void 0 },\n  { pattern: /%%ADVERTISING_ID_TYPE%%/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /%%ADVERTISING_ID%%/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /%%LIMIT_AD_TRACKING%%/gi, getValue: (ctx) => ctx.limitAdTracking != null ? ctx.limitAdTracking ? \"1\" : \"0\" : void 0 },\n  { pattern: /%%MSID%%/gi, getValue: (ctx) => ctx.appId },\n  { pattern: /%%APP_NAME%%/gi, getValue: (ctx) => ctx.appName },\n  { pattern: /%%SESSION_ID%%/gi, getValue: (ctx) => ctx.sessionId },\n  { pattern: /%%CORRELATOR%%/gi, getValue: (ctx) => ctx.correlator }\n];\nfunction isMacroPlaceholder2(value) {\n  if (value == null) return true;\n  const trimmed = value.trim();\n  if (!trimmed) return true;\n  if (UNEXPANDED_MACRO_PATTERN.test(trimmed)) return true;\n  return /^(unknown|null|undefined|none|n\\/a|\\$\\{[^}]+\\})$/i.test(trimmed);\n}\nfunction generateCorrelator() {\n  if (typeof crypto !== \"undefined\" && crypto.getRandomValues) {\n    try {\n      const buf = new Uint32Array(2);\n      crypto.getRandomValues(buf);\n      const value = (buf[0] ?? 0) * 2097152 + ((buf[1] ?? 0) & 2097151);\n      if (value > 0) {\n        return String(value);\n      }\n    } catch {\n    }\n  }\n  return String(Math.floor(Math.random() * Number.MAX_SAFE_INTEGER) + 1);\n}\nfunction expandInlineMacroPlaceholders(baseUrl, ctx) {\n  let url = baseUrl;\n  for (const { pattern, getValue } of INLINE_DEVICE_MACRO_REPLACEMENTS) {\n    const value = getValue(ctx);\n    if (value != null && value !== \"\") {\n      url = url.replace(pattern, encodeURIComponent(value));\n    }\n  }\n  return url;\n}\nfunction applyDeviceIdentityParams(params, ctx) {\n  const runtimeId = ctx.deviceId?.trim();\n  const runtimeType = ctx.deviceIdType?.trim() || inferDeviceIdType();\n  const tagRdid = params.get(\"rdid\");\n  const tagType = params.get(\"idtype\");\n  const tagLat = params.get(\"is_lat\");\n  const latValue = ctx.limitAdTracking != null ? ctx.limitAdTracking ? \"1\" : \"0\" : void 0;\n  if (runtimeId) {\n    params.set(\"rdid\", runtimeId);\n    params.set(\"idtype\", runtimeType || tagType || \"aaid\");\n    params.set(\"is_lat\", latValue ?? (isMacroPlaceholder2(tagLat) ? \"0\" : tagLat));\n    return;\n  }\n  const tagRdidValid = Boolean(tagRdid && !isMacroPlaceholder2(tagRdid));\n  const tagTypeValid = Boolean(tagType && !isMacroPlaceholder2(tagType));\n  if (tagRdidValid && tagTypeValid && runtimeType && !isEquivalentDeviceIdType(tagType, runtimeType)) {\n    params.delete(\"rdid\");\n    params.delete(\"idtype\");\n    params.delete(\"is_lat\");\n    return;\n  }\n  if (tagRdidValid) {\n    if (isMacroPlaceholder2(tagType) && runtimeType) {\n      params.set(\"idtype\", runtimeType);\n    }\n    if (isMacroPlaceholder2(tagLat)) {\n      params.set(\"is_lat\", latValue ?? \"0\");\n    }\n    return;\n  }\n  params.delete(\"rdid\");\n  params.delete(\"idtype\");\n  params.delete(\"is_lat\");\n}\nfunction removeBrokenAppNameOrphans(params, appName) {\n  const toDelete = [];\n  params.forEach((_value, key) => {\n    if (!key || INVALID_VAST_PARAM_KEY.test(key)) {\n      toDelete.push(key);\n    }\n  });\n  if (appName && appName.includes(\"&\")) {\n    for (const suffix of appName.split(\"&\").slice(1)) {\n      const trimmed = suffix.replace(/^\\s+/, \"\");\n      if (!trimmed) continue;\n      toDelete.push(suffix, ` ${trimmed}`, trimmed);\n    }\n  }\n  for (const key of new Set(toDelete)) {\n    if (key) params.delete(key);\n  }\n}\nfunction normalizeVastTagUrl(raw) {\n  if (!raw) return raw;\n  try {\n    const url = new URL(raw);\n    const anValue = url.searchParams.get(\"an\");\n    if (anValue !== null) {\n      const orphanFragments = [];\n      url.searchParams.forEach((_value, key) => {\n        if (key && INVALID_VAST_PARAM_KEY.test(key)) {\n          orphanFragments.push(key.trim());\n        }\n      });\n      if (orphanFragments.length > 0) {\n        const reconstructed = [anValue.replace(/\\s+$/, \"\"), ...orphanFragments].filter(Boolean).join(\" & \");\n        url.searchParams.forEach((_value, key) => {\n          if (key && INVALID_VAST_PARAM_KEY.test(key)) {\n            url.searchParams.delete(key);\n          }\n        });\n        url.searchParams.set(\"an\", reconstructed);\n        return url.toString().replace(\n          /([?&]an=)([^&]*)/,\n          (_match, prefix, val) => prefix + val.replace(/\\+/g, \"%20\")\n        );\n      }\n    }\n    removeBrokenAppNameOrphans(url.searchParams);\n    return url.toString();\n  } catch {\n    return raw;\n  }\n}\nfunction applyVastMacros(baseUrl, ctx) {\n  const expandedUrl = expandInlineMacroPlaceholders(baseUrl, ctx);\n  let url;\n  try {\n    url = new URL(normalizeVastTagUrl(expandedUrl));\n  } catch {\n    return replaceCorrelatorFallback(expandedUrl, ctx.correlator);\n  }\n  const params = url.searchParams;\n  removeBrokenAppNameOrphans(params, ctx.appName);\n  params.set(\"correlator\", ctx.correlator);\n  params.set(\"scor\", ctx.streamCorrelator);\n  if (ctx.isCtv) {\n    for (const key of CTV_UNSUPPORTED_PARAMS) {\n      params.delete(key);\n    }\n  }\n  if (ctx.pod != null) {\n    params.set(\"pod\", String(ctx.pod));\n  }\n  params.delete(\"ppos\");\n  params.delete(\"lip\");\n  if (ctx.podMinDurationMs != null) {\n    params.set(\"pmnd\", String(Math.max(0, Math.round(ctx.podMinDurationMs))));\n  }\n  if (ctx.podMaxDurationMs != null) {\n    params.set(\"pmxd\", String(Math.max(0, Math.round(ctx.podMaxDurationMs))));\n  }\n  if (ctx.podMaxAds != null) {\n    params.set(\"pmad\", String(Math.max(1, Math.round(ctx.podMaxAds))));\n  }\n  const requestUrl = ctx.contentUrl || ctx.pageUrl;\n  if (requestUrl) {\n    params.set(\"url\", requestUrl);\n    if (!ctx.isCtv) {\n      params.set(\"description_url\", requestUrl);\n    }\n  } else {\n    const existingUrl = params.get(\"url\") || \"\";\n    if (EXAMPLE_COM_URL.test(existingUrl)) {\n      params.delete(\"url\");\n      params.delete(\"description_url\");\n    }\n  }\n  if (ctx.adWillPlayMuted != null) {\n    params.set(\"vpmute\", ctx.adWillPlayMuted ? \"1\" : \"0\");\n  }\n  if (ctx.adWillAutoPlay != null) {\n    params.set(\"vpa\", ctx.adWillAutoPlay ? \"auto\" : \"click\");\n  }\n  if (ctx.appId) {\n    params.set(\"msid\", ctx.appId);\n  }\n  if (ctx.appName) {\n    removeBrokenAppNameOrphans(params, ctx.appName);\n    params.set(\"an\", ctx.appName);\n  }\n  if (ctx.sessionId) {\n    params.set(\"sid\", ctx.sessionId);\n  }\n  if (ctx.deviceTypeHint != null) {\n    params.set(\"dth\", String(ctx.deviceTypeHint));\n  } else if (ctx.isCtv) {\n    params.set(\"dth\", \"5\");\n  }\n  applyDeviceIdentityParams(params, ctx);\n  if (!ctx.isCtv) {\n    const consent = ctx.consent;\n    if (consent?.gdpr != null) {\n      params.set(\"gdpr\", consent.gdpr);\n    }\n    if (consent?.gdprConsent != null) {\n      params.set(\"gdpr_consent\", consent.gdprConsent);\n    }\n    if (consent?.usPrivacy != null) {\n      params.set(\"us_privacy\", consent.usPrivacy);\n    }\n  }\n  if (ctx.adTest) {\n    params.set(\"adtest\", \"on\");\n  }\n  const staleKeys = [];\n  params.forEach((value, key) => {\n    if (isMacroPlaceholder2(value)) {\n      staleKeys.push(key);\n    }\n  });\n  for (const key of staleKeys) {\n    params.delete(key);\n  }\n  removeBrokenAppNameOrphans(params, ctx.appName);\n  return url.toString();\n}\nfunction replaceCorrelatorFallback(baseUrl, correlator) {\n  const correlatorRegex = /([?&])correlator=([^&]*)/;\n  if (correlatorRegex.test(baseUrl)) {\n    return baseUrl.replace(correlatorRegex, `$1correlator=${correlator}`);\n  }\n  const sep = baseUrl.includes(\"?\") ? \"&\" : \"?\";\n  return `${baseUrl}${sep}correlator=${correlator}`;\n}\nfunction fetchConsentSignals(timeoutMs = 1500) {\n  const signals = {};\n  if (typeof window === \"undefined\") {\n    return Promise.resolve(signals);\n  }\n  const tasks = [];\n  const tcfApi = window.__tcfapi;\n  if (typeof tcfApi === \"function\") {\n    tasks.push(\n      new Promise((resolve) => {\n        let settled = false;\n        try {\n          tcfApi(\"addEventListener\", 2, (tcData, success) => {\n            if (settled) return;\n            if (success && tcData && (tcData.eventStatus === \"tcloaded\" || tcData.eventStatus === \"useractioncomplete\")) {\n              settled = true;\n              signals.gdpr = tcData.gdprApplies ? \"1\" : \"0\";\n              if (typeof tcData.tcString === \"string\" && tcData.tcString) {\n                signals.gdprConsent = tcData.tcString;\n              }\n              try {\n                tcfApi(\"removeEventListener\", 2, () => {\n                }, tcData.listenerId);\n              } catch {\n              }\n              resolve();\n            }\n          });\n        } catch {\n          resolve();\n        }\n        setTimeout(() => {\n          if (!settled) {\n            settled = true;\n            resolve();\n          }\n        }, timeoutMs);\n      })\n    );\n  }\n  const uspApi = window.__uspapi;\n  if (typeof uspApi === \"function\") {\n    tasks.push(\n      new Promise((resolve) => {\n        try {\n          uspApi(\"getUSPData\", 1, (data, success) => {\n            if (success && typeof data?.uspString === \"string\" && data.uspString) {\n              signals.usPrivacy = data.uspString;\n            }\n            resolve();\n          });\n        } catch {\n          resolve();\n        }\n        setTimeout(resolve, timeoutMs);\n      })\n    );\n  }\n  if (tasks.length === 0) {\n    return Promise.resolve(signals);\n  }\n  return Promise.all(tasks).then(() => signals);\n}\n\n// src/utils/browserCompat.ts\nfunction getChromeVersion(ua) {\n  const match = ua.match(/Chrome\\/(\\d+)/);\n  return match && match[1] ? parseInt(match[1], 10) : 0;\n}\nfunction getWebKitVersion(ua) {\n  const match = ua.match(/AppleWebKit\\/(\\d+)/);\n  return match && match[1] ? parseInt(match[1], 10) : 0;\n}\nfunction getPlatform() {\n  if (\"userAgentData\" in navigator && navigator.userAgentData?.platform) {\n    return navigator.userAgentData.platform;\n  }\n  const ua = navigator.userAgent;\n  if (/Mac|iPhone|iPad|iPod/i.test(ua)) {\n    return /iPhone|iPad|iPod/i.test(ua) ? \"iPhone\" : \"MacIntel\";\n  }\n  if (/Win/i.test(ua)) {\n    return \"Win32\";\n  }\n  if (/Linux/i.test(ua)) {\n    return /Android/i.test(ua) ? \"Linux armv8l\" : \"Linux x86_64\";\n  }\n  if (/CrOS/i.test(ua)) {\n    return \"CrOS\";\n  }\n  return navigator.platform || \"Unknown\";\n}\nfunction detectBrowser() {\n  const ua = navigator.userAgent;\n  const platform = getPlatform();\n  let name = \"Unknown\";\n  let version = \"0\";\n  let majorVersion = 0;\n  let isSmartTV = false;\n  let isLegacyTV = false;\n  let supportsModernJS = true;\n  let webOSVersion;\n  let tizenVersion;\n  let chromeVersionNum;\n  const chromeVersion = getChromeVersion(ua);\n  const webkitVersion = getWebKitVersion(ua);\n  chromeVersionNum = chromeVersion > 0 ? chromeVersion : void 0;\n  if (/Web0S|webOS|LG Browser|LGSTB/i.test(ua)) {\n    name = \"LG WebOS\";\n    isSmartTV = true;\n    let match = ua.match(/Web0S[/\\s]*([\\d.]+)/i) || ua.match(/webOS[/\\s]*([\\d.]+)/i);\n    if (!match || !match[1]) {\n      match = ua.match(/webOSTV[/\\s-]*([\\d.]+)/i) || ua.match(/webOS\\.TV[/\\s-]*([\\d.]+)/i);\n    }\n    if (match && match[1]) {\n      version = match[1];\n      const parts = version.split(\".\");\n      majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n      webOSVersion = majorVersion;\n    } else if (chromeVersion > 0) {\n      if (chromeVersion >= 79) {\n        webOSVersion = 6;\n        version = \"6.0\";\n        majorVersion = 6;\n      } else if (chromeVersion >= 68) {\n        webOSVersion = 5;\n        version = \"5.0\";\n        majorVersion = 5;\n      } else if (chromeVersion >= 53) {\n        webOSVersion = 4;\n        version = \"4.0\";\n        majorVersion = 4;\n      } else if (chromeVersion >= 38) {\n        webOSVersion = 3;\n        version = \"3.0\";\n        majorVersion = 3;\n      } else {\n        webOSVersion = 2;\n        version = \"2.0\";\n        majorVersion = 2;\n      }\n    } else {\n      version = \"Unknown\";\n      webOSVersion = void 0;\n    }\n    isLegacyTV = webOSVersion !== void 0 && webOSVersion < 3;\n  } else if (/Tizen/i.test(ua)) {\n    name = \"Samsung Tizen\";\n    isSmartTV = true;\n    const match = ua.match(/Tizen[/\\s]*([\\d.]+)/i);\n    version = match && match[1] ? match[1] : \"Unknown\";\n    if (version !== \"Unknown\") {\n      const parts = version.split(\".\");\n      majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n      tizenVersion = majorVersion;\n    }\n    isLegacyTV = tizenVersion !== void 0 && tizenVersion < 3;\n  } else if (/SMART-TV|SmartTV/i.test(ua)) {\n    name = \"Smart TV\";\n    isSmartTV = true;\n    isLegacyTV = chromeVersion > 0 && chromeVersion < 53;\n  } else if (/NetCast/i.test(ua)) {\n    name = \"LG NetCast\";\n    isSmartTV = true;\n    isLegacyTV = true;\n  } else if (/BRAVIA/i.test(ua)) {\n    name = \"Sony BRAVIA\";\n    isSmartTV = true;\n    isLegacyTV = chromeVersion > 0 && chromeVersion < 53;\n  } else {\n    if (chromeVersion > 0) {\n      name = \"Chrome\";\n      version = chromeVersion.toString();\n      majorVersion = chromeVersion;\n      if (chromeVersion < 50) {\n        supportsModernJS = false;\n      }\n    }\n    if (webkitVersion > 0 && webkitVersion < 600) {\n      supportsModernJS = false;\n    }\n  }\n  if (typeof Promise === \"undefined\" || typeof Map === \"undefined\" || typeof Set === \"undefined\") {\n    supportsModernJS = false;\n  }\n  if (typeof URLSearchParams === \"undefined\") {\n    supportsModernJS = false;\n  }\n  return {\n    name,\n    version,\n    majorVersion,\n    isSmartTV,\n    isLegacyTV,\n    platform,\n    supportsModernJS,\n    webOSVersion,\n    tizenVersion,\n    chromeVersion: chromeVersionNum\n  };\n}\nfunction getBrowserConfigOverrides() {\n  const browser = detectBrowser();\n  const overrides = {};\n  if (browser.isSmartTV) {\n    overrides.allowNativeHls = true;\n    overrides.pauseContentDuringAds = true;\n  }\n  return overrides;\n}\nfunction logBrowserInfo(debug = false) {\n  if (!debug) return;\n  const browser = detectBrowser();\n  console.log(\"[StormcloudVideoPlayer] Browser Compatibility Info:\", {\n    browser: `${browser.name} ${browser.version}`,\n    platform: browser.platform,\n    isSmartTV: browser.isSmartTV,\n    isLegacyTV: browser.isLegacyTV,\n    supportsModernJS: browser.supportsModernJS,\n    ...browser.webOSVersion !== void 0 ? { webOSVersion: browser.webOSVersion } : {},\n    ...browser.tizenVersion !== void 0 ? { tizenVersion: browser.tizenVersion } : {},\n    ...browser.chromeVersion !== void 0 ? { chromeVersion: browser.chromeVersion } : {},\n    userAgent: navigator.userAgent\n  });\n}\n\n// src/player/Scte35Parser.ts\nfunction parseCueOutDuration(value) {\n  const num = parseFloat(value.trim());\n  if (!Number.isNaN(num)) return num;\n  const match = value.match(/(?:^|[,\\s])DURATION\\s*=\\s*([0-9.]+)/i) || value.match(/Duration\\s*=\\s*([0-9.]+)/i);\n  if (match && match[1] != null) {\n    const dStr = match[1];\n    const d = parseFloat(dStr);\n    return Number.isNaN(d) ? void 0 : d;\n  }\n  return void 0;\n}\nfunction parseCueOutCont(value) {\n  const res = {};\n  const elapsedMatch = value.match(/Elapsed\\s*=\\s*([0-9.]+)/i);\n  const durationMatch = value.match(/Duration\\s*=\\s*([0-9.]+)/i);\n  if (elapsedMatch && elapsedMatch[1] != null) {\n    const e = parseFloat(elapsedMatch[1]);\n    if (!Number.isNaN(e)) res.elapsed = e;\n  }\n  if (durationMatch && durationMatch[1] != null) {\n    const d = parseFloat(durationMatch[1]);\n    if (!Number.isNaN(d)) res.duration = d;\n  }\n  if (!(\"elapsed\" in res) || !(\"duration\" in res)) {\n    const slashMatch = value.match(/([0-9.]+)\\s*\\/\\s*([0-9.]+)/);\n    if (slashMatch && slashMatch[1] && slashMatch[2]) {\n      const elapsed = parseFloat(slashMatch[1]);\n      const duration = parseFloat(slashMatch[2]);\n      if (!Number.isNaN(elapsed) && !(\"elapsed\" in res)) res.elapsed = elapsed;\n      if (!Number.isNaN(duration) && !(\"duration\" in res)) res.duration = duration;\n    }\n  }\n  if (\"elapsed\" in res || \"duration\" in res) return res;\n  return void 0;\n}\nfunction parseAttributeList(value) {\n  const attrs = {};\n  const regex = /([A-Z0-9-]+)=((\"[^\"]*\")|([^\",]*))(?:,|$)/gi;\n  let match;\n  while ((match = regex.exec(value)) !== null) {\n    const key = match[1] ?? \"\";\n    let rawVal = match[3] ?? match[4] ?? \"\";\n    if (rawVal.startsWith('\"') && rawVal.endsWith('\"')) {\n      rawVal = rawVal.slice(1, -1);\n    }\n    if (key) {\n      attrs[key] = rawVal;\n    }\n  }\n  return attrs;\n}\nfunction toNumber(val) {\n  if (val == null) return void 0;\n  const n = typeof val === \"string\" ? parseFloat(val) : Number(val);\n  return Number.isNaN(n) ? void 0 : n;\n}\nfunction isManifestBasedMarker(marker) {\n  const raw = marker.raw;\n  if (!raw) return false;\n  if (raw.tag) {\n    const tag = String(raw.tag);\n    return tag.includes(\"EXT-X-CUE-OUT\") || tag.includes(\"EXT-X-CUE-IN\") || tag.includes(\"EXT-X-DATERANGE\");\n  }\n  if (raw.id3) return false;\n  if (raw.splice_command_type) return false;\n  return false;\n}\nfunction decodeId3ValueToText(value) {\n  try {\n    if (typeof value === \"string\") return value;\n    const decoder = new TextDecoder(\"utf-8\", { fatal: false });\n    const text = decoder.decode(value);\n    if (text && /[\\x20-\\x7E]/.test(text)) return text;\n    let out = \"\";\n    for (let i = 0; i < value.length; i++)\n      out += String.fromCharCode(value[i]);\n    return out;\n  } catch {\n    return void 0;\n  }\n}\nfunction getFragmentStartSeconds(frag) {\n  const candidates = [frag?.start, frag?.startPTS];\n  for (const candidate of candidates) {\n    if (typeof candidate === \"number\" && Number.isFinite(candidate)) {\n      return candidate;\n    }\n  }\n  return void 0;\n}\nfunction parseScte35FromId3(tag) {\n  const text = decodeId3ValueToText(tag.value);\n  if (!text) return void 0;\n  const cueOutMatch = text.match(/EXT-X-CUE-OUT(?::([^\\r\\n]*))?/i) || text.match(/CUE-OUT(?::([^\\r\\n]*))?/i);\n  if (cueOutMatch) {\n    const arg = (cueOutMatch[1] ?? \"\").trim();\n    const dur = parseCueOutDuration(arg);\n    const marker = {\n      type: \"start\",\n      ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n      ...dur !== void 0 ? { durationSeconds: dur } : {},\n      raw: { id3: text }\n    };\n    return marker;\n  }\n  const cueOutContMatch = text.match(/EXT-X-CUE-OUT-CONT:([^\\r\\n]*)/i);\n  if (cueOutContMatch) {\n    const arg = (cueOutContMatch[1] ?? \"\").trim();\n    const cont = parseCueOutCont(arg);\n    const marker = {\n      type: \"progress\",\n      ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n      ...cont?.duration !== void 0 ? { durationSeconds: cont.duration } : {},\n      raw: { id3: text }\n    };\n    return marker;\n  }\n  const cueInMatch = text.match(/EXT-X-CUE-IN\\b/i) || text.match(/CUE-IN\\b/i);\n  if (cueInMatch) {\n    const marker = {\n      type: \"end\",\n      ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n      raw: { id3: text }\n    };\n    return marker;\n  }\n  const daterangeMatch = text.match(/EXT-X-DATERANGE:([^\\r\\n]*)/i);\n  if (daterangeMatch) {\n    const attrs = parseAttributeList(daterangeMatch[1] ?? \"\");\n    const hasScteOut = \"SCTE35-OUT\" in attrs || attrs[\"SCTE35-OUT\"] !== void 0;\n    const hasScteIn = \"SCTE35-IN\" in attrs || attrs[\"SCTE35-IN\"] !== void 0;\n    const klass = String(attrs[\"CLASS\"] ?? \"\");\n    const duration = toNumber(attrs[\"DURATION\"]);\n    if (hasScteOut || /com\\.apple\\.hls\\.cue/i.test(klass)) {\n      const marker = {\n        type: \"start\",\n        ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n        ...duration !== void 0 ? { durationSeconds: duration } : {},\n        raw: { id3: text, attrs }\n      };\n      return marker;\n    }\n    if (hasScteIn) {\n      const marker = {\n        type: \"end\",\n        ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n        raw: { id3: text, attrs }\n      };\n      return marker;\n    }\n  }\n  if (/SCTE35-OUT/i.test(text)) {\n    const marker = {\n      type: \"start\",\n      ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n      raw: { id3: text }\n    };\n    return marker;\n  }\n  if (/SCTE35-IN/i.test(text)) {\n    const marker = {\n      type: \"end\",\n      ...tag.ptsSeconds !== void 0 ? { ptsSeconds: tag.ptsSeconds } : {},\n      raw: { id3: text }\n    };\n    return marker;\n  }\n  if (tag.value instanceof Uint8Array) {\n    const bin = parseScte35Binary(tag.value);\n    if (bin) return bin;\n  }\n  return void 0;\n}\nfunction normalizeFragmentPayload(payload) {\n  if (payload instanceof Uint8Array) {\n    return payload;\n  }\n  if (payload instanceof ArrayBuffer) {\n    return new Uint8Array(payload);\n  }\n  if (ArrayBuffer.isView(payload)) {\n    const view = payload;\n    return new Uint8Array(view.buffer, view.byteOffset, view.byteLength);\n  }\n  return void 0;\n}\nfunction detectTsPacketFormat(data) {\n  const packetSizes = [188, 192, 204];\n  for (const packetSize of packetSizes) {\n    const tsPayloadOffset = packetSize === 192 ? 4 : 0;\n    for (let offset = 0; offset < packetSize; offset++) {\n      let matchedPackets = 0;\n      for (let packetStart = offset; packetStart + tsPayloadOffset < data.length && matchedPackets < 5; packetStart += packetSize) {\n        if (data[packetStart + tsPayloadOffset] !== 71) {\n          break;\n        }\n        matchedPackets++;\n      }\n      if (matchedPackets >= 2) {\n        return { offset, packetSize, tsPayloadOffset };\n      }\n    }\n  }\n  return void 0;\n}\nfunction getPsiSectionStart(payload, payloadUnitStart) {\n  if (!payloadUnitStart) {\n    return void 0;\n  }\n  const pointerField = payload[0];\n  if (pointerField == null) {\n    return void 0;\n  }\n  const sectionStart = 1 + pointerField;\n  return sectionStart < payload.length ? sectionStart : void 0;\n}\nfunction getPsiSectionLength(data, offset) {\n  return ((data[offset + 1] ?? 0) & 15) << 8 | (data[offset + 2] ?? 0);\n}\nfunction parsePatSection(payload, payloadUnitStart, pmtPids) {\n  const sectionStart = getPsiSectionStart(payload, payloadUnitStart);\n  if (sectionStart == null || sectionStart + 8 >= payload.length) {\n    return;\n  }\n  if (payload[sectionStart] !== 0) {\n    return;\n  }\n  const sectionLength = getPsiSectionLength(payload, sectionStart);\n  const sectionEnd = Math.min(\n    payload.length,\n    sectionStart + 3 + sectionLength\n  );\n  for (let offset = sectionStart + 8; offset + 4 <= sectionEnd - 4; offset += 4) {\n    const programNumber = (payload[offset] ?? 0) << 8 | (payload[offset + 1] ?? 0);\n    const pid = ((payload[offset + 2] ?? 0) & 31) << 8 | (payload[offset + 3] ?? 0);\n    if (programNumber !== 0) {\n      pmtPids.add(pid);\n    }\n  }\n}\nfunction descriptorsIdentifyScte35(data, start, end) {\n  let offset = start;\n  while (offset + 2 <= end) {\n    const tag = data[offset] ?? 0;\n    const length = data[offset + 1] ?? 0;\n    const descriptorStart = offset + 2;\n    const descriptorEnd = descriptorStart + length;\n    if (descriptorEnd > end) {\n      return false;\n    }\n    const registration = length >= 4 ? String.fromCharCode(\n      data[descriptorStart] ?? 0,\n      data[descriptorStart + 1] ?? 0,\n      data[descriptorStart + 2] ?? 0,\n      data[descriptorStart + 3] ?? 0\n    ) : \"\";\n    if (tag === 138 || registration === \"CUEI\" || registration === \"SCTE\") {\n      return true;\n    }\n    offset = descriptorEnd;\n  }\n  return false;\n}\nfunction parsePmtSection(payload, payloadUnitStart, tsScte35Pids) {\n  const sectionStart = getPsiSectionStart(payload, payloadUnitStart);\n  if (sectionStart == null || sectionStart + 12 >= payload.length) {\n    return;\n  }\n  if (payload[sectionStart] !== 2) {\n    return;\n  }\n  const sectionLength = getPsiSectionLength(payload, sectionStart);\n  const sectionEnd = Math.min(\n    payload.length,\n    sectionStart + 3 + sectionLength\n  );\n  const programInfoLength = ((payload[sectionStart + 10] ?? 0) & 15) << 8 | (payload[sectionStart + 11] ?? 0);\n  let offset = sectionStart + 12 + programInfoLength;\n  while (offset + 5 <= sectionEnd - 4) {\n    const streamType = payload[offset] ?? 0;\n    const elementaryPid = ((payload[offset + 1] ?? 0) & 31) << 8 | (payload[offset + 2] ?? 0);\n    const esInfoLength = ((payload[offset + 3] ?? 0) & 15) << 8 | (payload[offset + 4] ?? 0);\n    const descriptorStart = offset + 5;\n    const descriptorEnd = Math.min(descriptorStart + esInfoLength, sectionEnd - 4);\n    if (streamType === 134 || streamType === 6 && descriptorsIdentifyScte35(payload, descriptorStart, descriptorEnd)) {\n      tsScte35Pids.add(elementaryPid);\n    }\n    offset = descriptorStart + esInfoLength;\n  }\n}\nfunction hasProcessedTsScte35Section(section, processedSections) {\n  let checksum = 0;\n  for (let i = 0; i < section.length; i++) {\n    checksum = checksum * 31 + (section[i] ?? 0) >>> 0;\n  }\n  const key = `${section.length}:${checksum}`;\n  if (processedSections.has(key)) {\n    return true;\n  }\n  processedSections.add(key);\n  if (processedSections.size > 200) {\n    const firstKey = processedSections.values().next().value;\n    if (firstKey) {\n      processedSections.delete(firstKey);\n    }\n  }\n  return false;\n}\nfunction addScte35SectionMarker(section, markers, processedSections) {\n  if (section[0] !== 252 || hasProcessedTsScte35Section(section, processedSections)) {\n    return;\n  }\n  const marker = parseScte35Binary(section);\n  if (!marker) {\n    return;\n  }\n  marker.raw = {\n    ...typeof marker.raw === \"object\" && marker.raw ? marker.raw : {},\n    source: \"ts-packet\"\n  };\n  markers.push(marker);\n}\nfunction appendScte35Bytes(pid, bytes, assemblers, markers, processedSections) {\n  const assembler = assemblers.get(pid);\n  if (!assembler) {\n    return;\n  }\n  for (let i = 0; i < bytes.length && assembler.bytes.length < assembler.expectedLength; i++) {\n    assembler.bytes.push(bytes[i] ?? 0);\n  }\n  if (assembler.bytes.length >= assembler.expectedLength) {\n    assemblers.delete(pid);\n    addScte35SectionMarker(new Uint8Array(assembler.bytes), markers, processedSections);\n  }\n}\nfunction collectScte35SectionsFromPayload(pid, payload, payloadUnitStart, assemblers, markers, processedSections) {\n  if (payload.length === 0) {\n    return;\n  }\n  let offset = 0;\n  if (payloadUnitStart) {\n    const pointerField = payload[0] ?? 0;\n    const previousAssembler = assemblers.get(pid);\n    if (previousAssembler && pointerField > 0) {\n      appendScte35Bytes(\n        pid,\n        payload.subarray(1, Math.min(1 + pointerField, payload.length)),\n        assemblers,\n        markers,\n        processedSections\n      );\n    }\n    assemblers.delete(pid);\n    offset = 1 + pointerField;\n  } else {\n    appendScte35Bytes(pid, payload, assemblers, markers, processedSections);\n    return;\n  }\n  while (offset + 3 <= payload.length) {\n    const tableId = payload[offset];\n    if (tableId == null || tableId === 255) {\n      return;\n    }\n    const sectionLength = getPsiSectionLength(payload, offset);\n    const totalLength = 3 + sectionLength;\n    if (sectionLength <= 0 || totalLength <= 3) {\n      return;\n    }\n    if (offset + totalLength <= payload.length) {\n      addScte35SectionMarker(\n        payload.subarray(offset, offset + totalLength),\n        markers,\n        processedSections\n      );\n      offset += totalLength;\n    } else {\n      assemblers.set(pid, {\n        bytes: Array.from(payload.subarray(offset)),\n        expectedLength: totalLength\n      });\n      return;\n    }\n  }\n}\nfunction parseScte35FromTsPackets(data, tsScte35Pids, pmtPids, processedSections) {\n  const packetInfo = detectTsPacketFormat(data);\n  if (!packetInfo) {\n    return [];\n  }\n  const markers = [];\n  const sectionAssemblers = /* @__PURE__ */ new Map();\n  for (let packetStart = packetInfo.offset; packetStart + packetInfo.packetSize <= data.length; packetStart += packetInfo.packetSize) {\n    const tsStart = packetStart + packetInfo.tsPayloadOffset;\n    if (data[tsStart] !== 71) {\n      continue;\n    }\n    const secondByte = data[tsStart + 1];\n    const thirdByte = data[tsStart + 2];\n    const fourthByte = data[tsStart + 3];\n    if (secondByte == null || thirdByte == null || fourthByte == null || (secondByte & 128) !== 0) {\n      continue;\n    }\n    const payloadUnitStart = (secondByte & 64) !== 0;\n    const pid = (secondByte & 31) << 8 | thirdByte;\n    const adaptationFieldControl = fourthByte >> 4 & 3;\n    const hasPayload = adaptationFieldControl === 1 || adaptationFieldControl === 3;\n    if (!hasPayload) {\n      continue;\n    }\n    let payloadStart = tsStart + 4;\n    if (adaptationFieldControl === 3) {\n      const adaptationLength = data[payloadStart];\n      if (adaptationLength == null) {\n        continue;\n      }\n      payloadStart += 1 + adaptationLength;\n    }\n    const payloadEnd = Math.min(tsStart + 188, data.length);\n    if (payloadStart >= payloadEnd || payloadStart >= data.length) {\n      continue;\n    }\n    const payload = data.subarray(payloadStart, payloadEnd);\n    if (pid === 0) {\n      parsePatSection(payload, payloadUnitStart, pmtPids);\n    } else if (pmtPids.has(pid)) {\n      parsePmtSection(payload, payloadUnitStart, tsScte35Pids);\n    } else if (tsScte35Pids.has(pid)) {\n      collectScte35SectionsFromPayload(\n        pid,\n        payload,\n        payloadUnitStart,\n        sectionAssemblers,\n        markers,\n        processedSections\n      );\n    }\n  }\n  return markers;\n}\nvar BitReader = class {\n  constructor(buf) {\n    this.buf = buf;\n    this.bytePos = 0;\n    this.bitPos = 0;\n  }\n  readBits(numBits) {\n    let result = 0;\n    while (numBits > 0) {\n      if (this.bytePos >= this.buf.length) return result;\n      const remainingInByte = 8 - this.bitPos;\n      const toRead = Math.min(numBits, remainingInByte);\n      const currentByte = this.buf[this.bytePos];\n      const shift = remainingInByte - toRead;\n      const mask = (1 << toRead) - 1 & 255;\n      const bits = currentByte >> shift & mask;\n      result = result << toRead | bits;\n      this.bitPos += toRead;\n      if (this.bitPos >= 8) {\n        this.bitPos = 0;\n        this.bytePos += 1;\n      }\n      numBits -= toRead;\n    }\n    return result >>> 0;\n  }\n  skipBits(n) {\n    this.readBits(n);\n  }\n  get bytePosition() {\n    return this.bitPos === 0 ? this.bytePos : this.bytePos + 1;\n  }\n};\nfunction readSpliceTime(r, ptsAdjustmentTicks) {\n  const timeSpecifiedFlag = r.readBits(1) === 1;\n  if (!timeSpecifiedFlag) {\n    r.readBits(7);\n    return void 0;\n  }\n  r.readBits(6);\n  const high = r.readBits(1);\n  const low = r.readBits(32);\n  const ptsTicks = (high * 4294967296 + low + ptsAdjustmentTicks) % 8589934592;\n  return ptsTicks / 9e4;\n}\nfunction markerTypeFromSegmentationTypeId(segmentationTypeId) {\n  switch (segmentationTypeId) {\n    case 16:\n    case 34:\n    case 48:\n    case 50:\n    case 52:\n    case 54:\n      return \"start\";\n    case 17:\n    case 35:\n    case 49:\n    case 51:\n    case 53:\n    case 55:\n      return \"end\";\n    default:\n      return void 0;\n  }\n}\nfunction parseScte35SegmentationDescriptor(descriptor) {\n  if (descriptor.length < 11) {\n    return void 0;\n  }\n  const identifier = String.fromCharCode(\n    descriptor[0] ?? 0,\n    descriptor[1] ?? 0,\n    descriptor[2] ?? 0,\n    descriptor[3] ?? 0\n  );\n  if (identifier !== \"CUEI\") {\n    return void 0;\n  }\n  const segmentationEventId = (descriptor[4] ?? 0) * 16777216 + ((descriptor[5] ?? 0) << 16) + ((descriptor[6] ?? 0) << 8) + (descriptor[7] ?? 0);\n  const cancelIndicator = ((descriptor[8] ?? 0) & 128) !== 0;\n  if (cancelIndicator) {\n    return void 0;\n  }\n  const flags = descriptor[9] ?? 0;\n  const programSegmentationFlag = (flags & 128) !== 0;\n  const segmentationDurationFlag = (flags & 64) !== 0;\n  let offset = 10;\n  if (!programSegmentationFlag) {\n    const componentCount = descriptor[offset] ?? 0;\n    offset += 1 + componentCount * 6;\n    if (offset > descriptor.length) {\n      return void 0;\n    }\n  }\n  let durationSeconds = void 0;\n  if (segmentationDurationFlag) {\n    if (offset + 5 > descriptor.length) {\n      return void 0;\n    }\n    const durationTicks = (descriptor[offset] ?? 0) * 4294967296 + (descriptor[offset + 1] ?? 0) * 16777216 + ((descriptor[offset + 2] ?? 0) << 16) + ((descriptor[offset + 3] ?? 0) << 8) + (descriptor[offset + 4] ?? 0);\n    durationSeconds = durationTicks / 9e4;\n    offset += 5;\n  }\n  if (offset + 2 > descriptor.length) {\n    return void 0;\n  }\n  offset += 1;\n  const segmentationUpidLength = descriptor[offset] ?? 0;\n  offset += 1 + segmentationUpidLength;\n  if (offset >= descriptor.length) {\n    return void 0;\n  }\n  const segmentationTypeId = descriptor[offset] ?? 0;\n  const markerType = markerTypeFromSegmentationTypeId(segmentationTypeId);\n  if (!markerType) {\n    return void 0;\n  }\n  return {\n    type: markerType,\n    ...durationSeconds !== void 0 ? { durationSeconds } : {},\n    segmentationEventId\n  };\n}\nfunction parseScte35SegmentationDescriptors(data, offset) {\n  if (offset + 2 > data.length) {\n    return void 0;\n  }\n  const descriptorLoopLength = (data[offset] ?? 0) << 8 | (data[offset + 1] ?? 0);\n  let descriptorOffset = offset + 2;\n  const descriptorEnd = Math.min(\n    data.length,\n    descriptorOffset + descriptorLoopLength\n  );\n  while (descriptorOffset + 2 <= descriptorEnd) {\n    const descriptorTag = data[descriptorOffset] ?? 0;\n    const descriptorLength = data[descriptorOffset + 1] ?? 0;\n    const descriptorDataStart = descriptorOffset + 2;\n    const descriptorDataEnd = descriptorDataStart + descriptorLength;\n    if (descriptorDataEnd > descriptorEnd) {\n      return void 0;\n    }\n    if (descriptorTag === 2) {\n      const descriptorMarker = parseScte35SegmentationDescriptor(\n        data.subarray(descriptorDataStart, descriptorDataEnd)\n      );\n      if (descriptorMarker) {\n        return descriptorMarker;\n      }\n    }\n    descriptorOffset = descriptorDataEnd;\n  }\n  return void 0;\n}\nfunction parseScte35Binary(data) {\n  const r = new BitReader(data);\n  const tableId = r.readBits(8);\n  if (tableId !== 252) return void 0;\n  r.readBits(1);\n  r.readBits(1);\n  r.readBits(2);\n  const sectionLength = r.readBits(12);\n  if (sectionLength <= 0 || data.length < 3 + sectionLength) {\n    return void 0;\n  }\n  r.readBits(8);\n  r.readBits(1);\n  r.readBits(6);\n  const ptsAdjHigh = r.readBits(1);\n  const ptsAdjLow = r.readBits(32);\n  const ptsAdjustmentTicks = ptsAdjHigh * 4294967296 + ptsAdjLow;\n  r.readBits(8);\n  r.readBits(12);\n  const spliceCommandLength = r.readBits(12);\n  const spliceCommandType = r.readBits(8);\n  let markerType;\n  let durationSeconds = void 0;\n  let ptsSeconds = void 0;\n  let spliceEventId = void 0;\n  const commandBodyStart = r.bytePosition;\n  if (spliceCommandType === 5) {\n    spliceEventId = r.readBits(32);\n    const cancel = r.readBits(1) === 1;\n    r.readBits(7);\n    if (cancel) return void 0;\n    const outOfNetwork = r.readBits(1) === 1;\n    const programSpliceFlag = r.readBits(1) === 1;\n    const durationFlag = r.readBits(1) === 1;\n    const spliceImmediateFlag = r.readBits(1) === 1;\n    r.readBits(4);\n    markerType = outOfNetwork ? \"start\" : \"end\";\n    if (programSpliceFlag && !spliceImmediateFlag) {\n      ptsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n    } else if (!programSpliceFlag) {\n      const componentCount = r.readBits(8);\n      for (let i = 0; i < componentCount; i++) {\n        r.readBits(8);\n        if (!spliceImmediateFlag) {\n          const componentPtsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n          if (ptsSeconds === void 0) {\n            ptsSeconds = componentPtsSeconds;\n          }\n        }\n      }\n    }\n    if (durationFlag) {\n      r.readBits(6);\n      r.readBits(1);\n      const high = r.readBits(1);\n      const low = r.readBits(32);\n      const durationTicks = high * 4294967296 + low;\n      durationSeconds = durationTicks / 9e4;\n    }\n    r.readBits(16);\n    r.readBits(8);\n    r.readBits(8);\n  } else if (spliceCommandType === 6) {\n    ptsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n  } else {\n    return void 0;\n  }\n  const expectedDescriptorOffset = spliceCommandLength === 4095 ? r.bytePosition : commandBodyStart + spliceCommandLength;\n  const descriptorMarker = parseScte35SegmentationDescriptors(\n    data,\n    expectedDescriptorOffset\n  );\n  if (descriptorMarker) {\n    markerType = descriptorMarker.type;\n    if (durationSeconds === void 0) {\n      durationSeconds = descriptorMarker.durationSeconds;\n    }\n  }\n  if (!markerType) {\n    return void 0;\n  }\n  const marker = {\n    type: markerType,\n    ...ptsSeconds !== void 0 ? { ptsSeconds } : {},\n    ...durationSeconds !== void 0 ? { durationSeconds } : {},\n    raw: {\n      splice_command_type: spliceCommandType,\n      ...spliceEventId !== void 0 ? { splice_event_id: spliceEventId } : {},\n      ...descriptorMarker?.segmentationEventId !== void 0 ? { segmentation_event_id: descriptorMarker.segmentationEventId } : {}\n    }\n  };\n  return marker;\n}\n\n// src/player/Scte35CueManager.ts\nvar Scte35CueManager = class {\n  constructor(debug, callbacks) {\n    this.pendingScte35Cues = /* @__PURE__ */ new Map();\n    this.recentScte35CueKeys = /* @__PURE__ */ new Map();\n    this.recentScte35CueLimit = 200;\n    this.tsScte35Pids = /* @__PURE__ */ new Set();\n    this.pmtPids = /* @__PURE__ */ new Set();\n    this.processedTsScte35Sections = /* @__PURE__ */ new Set();\n    this.debug = debug;\n    this.callbacks = callbacks;\n  }\n  get pendingScte35CueKey() {\n    return this.pendingScte35CueKeyValue;\n  }\n  set pendingScte35CueKey(value) {\n    this.pendingScte35CueKeyValue = value;\n  }\n  get activeScte35BreakKey() {\n    return this.activeScte35BreakKeyValue;\n  }\n  set activeScte35BreakKey(value) {\n    this.activeScte35BreakKeyValue = value;\n  }\n  get scheduledScte35BreakKey() {\n    return this.scheduledScte35BreakKeyValue;\n  }\n  set scheduledScte35BreakKey(value) {\n    this.scheduledScte35BreakKeyValue = value;\n  }\n  createScte35CueContext(source, readiness, frag) {\n    const context = { source, readiness };\n    if (typeof frag?.sn === \"number\") {\n      context.fragmentSn = frag.sn;\n    }\n    const fragmentStartSec = getFragmentStartSeconds(frag);\n    if (fragmentStartSec !== void 0) {\n      context.fragmentStartSeconds = fragmentStartSec;\n    }\n    return context;\n  }\n  onScte35Cue(marker, context) {\n    const cue = this.createScte35Cue(marker, context);\n    const pendingKey = this.getPendingScte35CueKey(cue);\n    if (context.readiness === \"early\") {\n      this.pendingScte35Cues.set(pendingKey, cue);\n      this.trimRecentScte35CueMaps();\n      if (marker.type === \"start\") {\n        this.callbacks.onEarlyStartCue(marker, context.fragmentSn, cue.key);\n      }\n      return;\n    }\n    if (marker.type === \"end\" && !this.shouldAcceptScte35EndCue(cue)) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Ignoring SCTE-35 end cue\", {\n          key: cue.key,\n          activeScte35BreakKey: this.activeScte35BreakKeyValue,\n          inAdBreak: this.callbacks.isInAdBreak(),\n          source: cue.source\n        });\n      }\n      return;\n    }\n    if (marker.type === \"start\" && this.hasRecentlyHandledScte35Cue(cue)) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Ignoring duplicate SCTE-35 start cue\", {\n          key: cue.key,\n          source: cue.source\n        });\n      }\n      return;\n    }\n    this.pendingScte35Cues.delete(pendingKey);\n    this.markScte35CueHandled(cue);\n    this.callbacks.onPlaybackCue(marker, cue.key);\n  }\n  activatePendingScte35CuesForFragment(frag) {\n    const fragmentSn = typeof frag?.sn === \"number\" ? frag.sn : void 0;\n    if (fragmentSn === void 0) {\n      return;\n    }\n    const matchingCues = Array.from(this.pendingScte35Cues.entries()).filter(\n      ([, cue]) => cue.fragmentSn === fragmentSn\n    );\n    matchingCues.forEach(([pendingKey, cue]) => {\n      this.pendingScte35Cues.delete(pendingKey);\n      const context = {\n        source: cue.source,\n        readiness: \"playback\"\n      };\n      context.fragmentSn = fragmentSn;\n      const fragmentStartSec = cue.fragmentStartSeconds ?? getFragmentStartSeconds(frag);\n      if (fragmentStartSec !== void 0) {\n        context.fragmentStartSeconds = fragmentStartSec;\n      }\n      this.onScte35Cue(cue.marker, context);\n    });\n  }\n  createScte35Cue(marker, context) {\n    const cue = {\n      marker,\n      source: context.source,\n      readiness: context.readiness,\n      key: this.getScte35CueKey(marker, context)\n    };\n    if (context.fragmentSn !== void 0) {\n      cue.fragmentSn = context.fragmentSn;\n    }\n    if (context.fragmentStartSeconds !== void 0) {\n      cue.fragmentStartSeconds = context.fragmentStartSeconds;\n    }\n    return cue;\n  }\n  getScte35CueKey(marker, context) {\n    const raw = this.getScte35MarkerRaw(marker);\n    const spliceEventId = this.toIdentityString(raw?.splice_event_id);\n    if (spliceEventId) {\n      return `splice:${spliceEventId}`;\n    }\n    const segmentationEventId = this.toIdentityString(raw?.segmentation_event_id);\n    if (segmentationEventId) {\n      return `segmentation:${segmentationEventId}`;\n    }\n    const daterangeId = this.toIdentityString(raw?.attrs?.ID);\n    if (daterangeId) {\n      return `daterange:${daterangeId}`;\n    }\n    const scteValue = this.toIdentityString(raw?.attrs?.[\"SCTE35-OUT\"]) || this.toIdentityString(raw?.attrs?.[\"SCTE35-IN\"]);\n    if (scteValue) {\n      return `daterange-scte:${scteValue}`;\n    }\n    if (typeof marker.ptsSeconds === \"number\" && Number.isFinite(marker.ptsSeconds)) {\n      return `pts:${Math.round(marker.ptsSeconds * 2) / 2}`;\n    }\n    if (context.fragmentSn !== void 0) {\n      return `fragment:${context.fragmentSn}`;\n    }\n    return `${context.source}:wallclock:${Math.floor(Date.now() / 1e3)}`;\n  }\n  getPendingScte35CueKey(cue) {\n    return `${cue.marker.type}:${cue.key}:${cue.fragmentSn !== void 0 ? cue.fragmentSn : \"unknown\"}`;\n  }\n  getScte35MarkerRaw(marker) {\n    return typeof marker.raw === \"object\" && marker.raw !== null ? marker.raw : {};\n  }\n  toIdentityString(value) {\n    if (typeof value === \"number\" && Number.isFinite(value)) {\n      return String(value);\n    }\n    if (typeof value === \"string\" && value.trim().length > 0) {\n      return value.trim();\n    }\n    return void 0;\n  }\n  isStrongScte35CueKey(key) {\n    return !!(key && (key.startsWith(\"splice:\") || key.startsWith(\"segmentation:\") || key.startsWith(\"daterange:\") || key.startsWith(\"daterange-scte:\")));\n  }\n  hasRecentlyHandledScte35Cue(cue) {\n    if (this.activeScte35BreakKeyValue === cue.key || this.scheduledScte35BreakKeyValue === cue.key) {\n      return true;\n    }\n    const recentKey = `${cue.marker.type}:${cue.key}`;\n    return this.recentScte35CueKeys.has(recentKey);\n  }\n  markScte35CueHandled(cue) {\n    this.recentScte35CueKeys.set(`${cue.marker.type}:${cue.key}`, Date.now());\n    this.trimRecentScte35CueMaps();\n  }\n  trimRecentScte35CueMaps() {\n    while (this.recentScte35CueKeys.size > this.recentScte35CueLimit) {\n      const firstKey = this.recentScte35CueKeys.keys().next().value;\n      if (!firstKey) {\n        break;\n      }\n      this.recentScte35CueKeys.delete(firstKey);\n    }\n    while (this.pendingScte35Cues.size > this.recentScte35CueLimit) {\n      const firstKey = this.pendingScte35Cues.keys().next().value;\n      if (!firstKey) {\n        break;\n      }\n      this.pendingScte35Cues.delete(firstKey);\n    }\n  }\n  shouldAcceptScte35EndCue(cue) {\n    if (!this.callbacks.isInAdBreak()) {\n      return false;\n    }\n    if (this.isStrongScte35CueKey(this.activeScte35BreakKeyValue) && this.isStrongScte35CueKey(cue.key) && this.activeScte35BreakKeyValue !== cue.key) {\n      return false;\n    }\n    return true;\n  }\n};\n\n// src/player/AdConfigManager.ts\nvar AdConfigManager = class {\n  constructor(config, video) {\n    this.vmapBreaks = [];\n    this.consumedVmapBreakIds = /* @__PURE__ */ new Set();\n    this.streamCorrelator = generateCorrelator();\n    this.viewCorrelator = generateCorrelator();\n    this.consentSignals = {};\n    this.podCounter = 0;\n    this.podAssignedByPrefetch = false;\n    this.lastHeartbeatTime = 0;\n    this.defaultPodMaxAds = 6;\n    this.defaultPodMaxDurationMs = 12e4;\n    this.config = config;\n    this.video = video;\n  }\n  get debug() {\n    return !!this.config.debugAdTiming;\n  }\n  isVmapEnabled() {\n    return !!(this.config.isVmap && this.config.vmapUrl?.trim());\n  }\n  async fetchAdConfiguration() {\n    if (this.isVmapEnabled()) {\n      await this.fetchAndParseVmap(this.config.vmapUrl);\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] VMAP mode enabled\");\n      }\n      return;\n    }\n    const vastMode = this.config.vastMode || \"default\";\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] VAST mode:\", vastMode);\n    }\n    if (vastMode === \"adstorm\") {\n      if (!this.config.licenseKey) {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] AdStorm mode requires a license key\"\n          );\n        }\n        return;\n      }\n      const vastEndpoint = `https://adstorm.co/api-adstorm-dev/adstorm/vast/${this.config.licenseKey}`;\n      this.apiVastTagUrl = vastEndpoint;\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Using AdStorm VAST endpoint (adstorm mode):\",\n          vastEndpoint\n        );\n      }\n      return;\n    }\n    if (this.config.vastTagUrl) {\n      this.apiVastTagUrl = normalizeVastTagUrl(this.config.vastTagUrl);\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Using custom VAST tag URL:\",\n          this.apiVastTagUrl\n        );\n      }\n      return;\n    }\n    const apiUrl = \"https://adstorm.co/api-adstorm-dev/adstorm/ads/web\";\n    if (this.debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Fetching ad configuration from:\",\n        apiUrl\n      );\n    }\n    const headers = {};\n    if (this.config.licenseKey) {\n      headers[\"Authorization\"] = `Bearer ${this.config.licenseKey}`;\n    }\n    const response = await fetch(apiUrl, { headers });\n    if (!response.ok) {\n      if (this.debug) {\n        console.warn(\n          `[StormcloudVideoPlayer] Failed to fetch ad configuration: ${response.status}`\n        );\n      }\n      return;\n    }\n    const data = await response.json();\n    this.applyMqttConfigFromResponse(data);\n    const imaPayload = data.response?.ima?.[\"publisherdesk.ima\"]?.payload;\n    if (imaPayload) {\n      let decodedPayload = imaPayload;\n      try {\n        decodedPayload = decodeURIComponent(imaPayload);\n      } catch {\n        console.warn(\"[StormcloudVideoPlayer] imaPayload was not URI-encoded; using as-is:\", imaPayload);\n      }\n      console.log(\"[StormcloudVideoPlayer] Raw VAST tag URL (from API):\", decodedPayload);\n      this.apiVastTagUrl = normalizeVastTagUrl(decodedPayload);\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Normalized VAST tag URL:\",\n          this.apiVastTagUrl\n        );\n      }\n    } else {\n      if (this.debug) {\n        console.warn(\n          \"[StormcloudVideoPlayer] No VAST tag URL found in /ads/web response\"\n        );\n      }\n    }\n    const numberAds = data.response?.options?.vast?.cue_tones?.number_ads;\n    if (numberAds != null && numberAds > 0) {\n      this.apiNumberAds = numberAds;\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Number of ads per break from API:\",\n          this.apiNumberAds\n        );\n      }\n    }\n  }\n  applyMqttConfigFromResponse(data) {\n    const mqttConfig2 = data.response?.mqtt_config;\n    if (!mqttConfig2 || typeof mqttConfig2 !== \"object\") {\n      return;\n    }\n    applyMQTTConfig(mqttConfig2);\n    if (this.debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Applied MQTT config from /ads/web:\",\n        mqttConfig2\n      );\n    }\n  }\n  async fetchAndParseVmap(vmapUrl) {\n    if (!vmapUrl.trim()) {\n      return;\n    }\n    try {\n      const response = await fetch(vmapUrl);\n      if (!response.ok) {\n        throw new Error(`Failed to fetch VMAP (${response.status})`);\n      }\n      const vmapXml = await response.text();\n      this.vmapBreaks = this.parseVmapToBreaks(vmapXml);\n      this.consumedVmapBreakIds.clear();\n      if (this.debug) {\n        console.log(\n          `[StormcloudVideoPlayer] Loaded ${this.vmapBreaks.length} VMAP ad break(s) from:`,\n          vmapUrl\n        );\n      }\n    } catch (error) {\n      this.vmapBreaks = [];\n      this.consumedVmapBreakIds.clear();\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to load VMAP:\", error);\n      }\n    }\n  }\n  parseVmapToBreaks(vmapXml) {\n    if (typeof DOMParser === \"undefined\") {\n      return [];\n    }\n    const doc = new DOMParser().parseFromString(vmapXml, \"application/xml\");\n    if (doc.querySelector(\"parsererror\")) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Invalid VMAP XML received\");\n      }\n      return [];\n    }\n    const VMAP_NS = \"http://www.iab.net/videosuite/vmap\";\n    let adBreakNodes = Array.from(doc.getElementsByTagNameNS(VMAP_NS, \"AdBreak\"));\n    if (adBreakNodes.length === 0) {\n      adBreakNodes = Array.from(\n        doc.querySelectorAll(\"AdBreak, vmap\\\\:AdBreak\")\n      );\n    }\n    if (adBreakNodes.length === 0) {\n      adBreakNodes = Array.from(doc.getElementsByTagName(\"*\")).filter(\n        (el) => el.localName === \"AdBreak\"\n      );\n    }\n    const parsed = [];\n    adBreakNodes.forEach((node, index) => {\n      const timeOffsetRaw = (node.getAttribute(\"timeOffset\") || \"\").trim();\n      const startTimeMs = this.parseVmapTimeOffsetToMs(timeOffsetRaw);\n      if (startTimeMs == null) {\n        return;\n      }\n      let adTagNode = node.getElementsByTagNameNS(VMAP_NS, \"AdTagURI\")[0];\n      if (!adTagNode) {\n        adTagNode = node.querySelector(\"AdTagURI, vmap\\\\:AdTagURI\") ?? void 0;\n      }\n      const adTagUrl = (adTagNode?.textContent || \"\").trim();\n      if (!adTagUrl) {\n        return;\n      }\n      const breakId = node.getAttribute(\"breakId\") || `vmap-break-${index}-${timeOffsetRaw || \"unknown\"}`;\n      parsed.push({\n        id: breakId,\n        startTimeMs,\n        vastTagUrl: adTagUrl\n      });\n    });\n    parsed.sort((a, b) => {\n      const aStart = a.startTimeMs < 0 ? Number.MAX_SAFE_INTEGER : a.startTimeMs;\n      const bStart = b.startTimeMs < 0 ? Number.MAX_SAFE_INTEGER : b.startTimeMs;\n      return aStart - bStart;\n    });\n    return parsed;\n  }\n  parseVmapTimeOffsetToMs(timeOffset) {\n    if (!timeOffset) {\n      return void 0;\n    }\n    const normalized = timeOffset.trim().toLowerCase();\n    if (normalized === \"start\") {\n      return 0;\n    }\n    if (normalized === \"end\") {\n      return -1;\n    }\n    const hms = timeOffset.match(\n      /^(\\d{1,2}):(\\d{2}):(\\d{2})(?:\\.(\\d{1,3}))?$/\n    );\n    if (hms) {\n      const [, hh, mm, ss, ms = \"0\"] = hms;\n      const hours = Number(hh);\n      const minutes = Number(mm);\n      const seconds = Number(ss);\n      const millis = Number(ms.padEnd(3, \"0\").slice(0, 3));\n      return (hours * 3600 + minutes * 60 + seconds) * 1e3 + millis;\n    }\n    const percent = timeOffset.match(/^(\\d+(?:\\.\\d+)?)%$/);\n    if (percent) {\n      const ratio = Number(percent[1]) / 100;\n      const durationSec = this.video.duration;\n      if (Number.isFinite(durationSec) && durationSec > 0) {\n        return Math.floor(durationSec * 1e3 * ratio);\n      }\n      return void 0;\n    }\n    return void 0;\n  }\n  getAdBreakKey(adBreak) {\n    if (adBreak.id) {\n      return adBreak.id;\n    }\n    return `${adBreak.startTimeMs}-${adBreak.vastTagUrl || \"\"}`;\n  }\n  resolveBreakStartMs(adBreak) {\n    if (adBreak.startTimeMs >= 0) {\n      return adBreak.startTimeMs;\n    }\n    if (adBreak.startTimeMs === -1) {\n      const durationSec = this.video.duration;\n      if (Number.isFinite(durationSec) && durationSec > 0) {\n        return Math.floor(durationSec * 1e3);\n      }\n    }\n    return void 0;\n  }\n  findCurrentOrNextBreak(nowMs) {\n    const schedule = this.vmapBreaks;\n    let candidate;\n    const tol = this.config.driftToleranceMs ?? 1e3;\n    for (const b of schedule) {\n      if (this.consumedVmapBreakIds.has(this.getAdBreakKey(b))) {\n        continue;\n      }\n      const breakStartMs = this.resolveBreakStartMs(b);\n      if (breakStartMs == null) {\n        continue;\n      }\n      if (breakStartMs <= nowMs + tol && (candidate == null || breakStartMs > (this.resolveBreakStartMs(candidate) ?? 0))) {\n        candidate = b;\n      }\n    }\n    return candidate;\n  }\n  findBreakForTime(nowMs) {\n    const schedule = this.vmapBreaks;\n    for (const b of schedule) {\n      if (this.consumedVmapBreakIds.has(this.getAdBreakKey(b))) {\n        continue;\n      }\n      const breakStartMs = this.resolveBreakStartMs(b);\n      if (breakStartMs == null) {\n        continue;\n      }\n      if (b.durationMs) {\n        const end = breakStartMs + b.durationMs;\n        if (nowMs >= breakStartMs && nowMs < end) {\n          return b;\n        }\n        continue;\n      }\n      if (nowMs >= breakStartMs) {\n        return b;\n      }\n    }\n    return void 0;\n  }\n  selectVastTagsForBreak(b) {\n    if (!b || !b.vastTagUrl) return void 0;\n    if (b.vastTagUrl.includes(\",\")) {\n      return b.vastTagUrl.split(\",\").map((s) => s.trim()).filter((s) => s.length > 0);\n    }\n    return [b.vastTagUrl];\n  }\n  beginNewAdPod() {\n    this.podCounter++;\n  }\n  resolvePodParams(breakDurationMs) {\n    const maxDurationMs = breakDurationMs != null && breakDurationMs > 0 ? breakDurationMs : this.config.podMaxDurationMs != null && this.config.podMaxDurationMs > 0 ? this.config.podMaxDurationMs : this.defaultPodMaxDurationMs;\n    const maxAds = this.config.podMaxAds && this.config.podMaxAds > 0 ? this.config.podMaxAds : this.apiNumberAds && this.apiNumberAds > 0 ? this.apiNumberAds : this.defaultPodMaxAds;\n    const minDurationMs = this.config.podExactDuration && maxDurationMs != null ? maxDurationMs : 0;\n    return { maxAds, minDurationMs, maxDurationMs };\n  }\n  generatePodVastUrl(baseUrl, podParams, adPlayer, palNonce, inAdBreak) {\n    const adWillPlayMuted = inAdBreak ? adPlayer.getOriginalMutedState() : this.video.muted;\n    const envSignals = resolveVastEnvironmentSignals(!!this.config.ctvAdRequest);\n    const urlWithMacros = applyVastMacros(baseUrl, {\n      correlator: this.viewCorrelator,\n      streamCorrelator: this.streamCorrelator,\n      pod: this.podCounter > 0 ? this.podCounter : void 0,\n      podMaxAds: podParams.maxAds,\n      podMinDurationMs: podParams.minDurationMs,\n      podMaxDurationMs: podParams.maxDurationMs,\n      isCtv: envSignals.isCtv,\n      contentUrl: envSignals.contentUrl,\n      pageUrl: !envSignals.isCtv && typeof window !== \"undefined\" ? toDevSafeUrl(window.location.href) : void 0,\n      adWillPlayMuted,\n      adWillAutoPlay: !!this.config.autoplay,\n      appId: envSignals.appId,\n      appName: envSignals.appName,\n      sessionId: envSignals.sessionId,\n      deviceId: envSignals.deviceId,\n      deviceIdType: envSignals.deviceIdType,\n      limitAdTracking: envSignals.limitAdTracking,\n      deviceTypeHint: envSignals.deviceTypeHint,\n      adTest: this.config.adTest,\n      consent: this.consentSignals\n    });\n    const finalUrl = palNonce.injectNonce(urlWithMacros);\n    console.log(\n      `[StormcloudVideoPlayer] Resolved optimized-pod request URL (pod=${this.podCounter}, pmad=${podParams.maxAds}, pmnd=${podParams.minDurationMs}, pmxd=${podParams.maxDurationMs ?? \"?\"}):`,\n      finalUrl\n    );\n    return finalUrl;\n  }\n  // --- Tracking ---\n  initializeTracking() {\n    sendInitialTracking(this.config.licenseKey, buildAnalyticsContext(this.config)).then(() => {\n      this.heartbeatInterval = window.setInterval(() => {\n        this.sendHeartbeatIfNeeded();\n      }, 5e3);\n    }).catch((error) => {\n      if (this.debug) {\n        console.warn(\n          \"[StormcloudVideoPlayer] Failed to send initial tracking:\",\n          error\n        );\n      }\n      this.heartbeatInterval = window.setInterval(() => {\n        this.sendHeartbeatIfNeeded();\n      }, 5e3);\n    });\n  }\n  sendHeartbeatIfNeeded() {\n    const now = Date.now();\n    if (!this.lastHeartbeatTime || now - this.lastHeartbeatTime > 3e4) {\n      this.lastHeartbeatTime = now;\n      sendHeartbeat(this.config.licenseKey, buildAnalyticsContext(this.config)).catch((error) => {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] Failed to send heartbeat:\",\n            error\n          );\n        }\n      });\n    }\n  }\n  destroyTracking() {\n    if (this.heartbeatInterval) {\n      clearInterval(this.heartbeatInterval);\n      this.heartbeatInterval = void 0;\n    }\n  }\n};\n\n// src/player/AdTimingService.ts\nvar AdTimingService = class {\n  constructor(config, video, callbacks) {\n    this.adRequestWatchdogToken = null;\n    this.adFailsafeToken = null;\n    this.ptsDriftEmaMs = 0;\n    this.adBreakPlayedDurationMs = 0;\n    this.adBreakEpoch = 0;\n    this.adRequestTokenCounter = 0;\n    this.activeAdRequestToken = null;\n    this.currentAdIndex = 0;\n    this.totalAdsInBreak = 0;\n    this.totalAdRequestsInBreak = 0;\n    this.maxTotalAdRequestsPerBreak = 10;\n    this.lastAdRequestTime = 0;\n    this.consecutiveFailures = 0;\n    this.maxConsecutiveFailures = 5;\n    this.minAdRequestIntervalMs = 3e3;\n    this.backoffBaseMs = 1e3;\n    this.maxBackoffMs = 15e3;\n    this.defaultMinRemainingMsToStartAd = 4e3;\n    this.failedVastUrls = /* @__PURE__ */ new Set();\n    this.temporaryFailureUrls = /* @__PURE__ */ new Map();\n    this.temporaryFailureCooldownMs = 3e4;\n    this.globalConsecutiveNoFills = 0;\n    this.globalNoFillThreshold = 3;\n    this.globalNoFillCooldownUntil = 0;\n    this.globalNoFillBackoffBaseMs = 5e3;\n    this.globalNoFillBackoffMaxMs = 6e4;\n    this.globalLastGamRequestTime = 0;\n    this.globalMinGamIntervalMs = 3e3;\n    this.config = config;\n    this.video = video;\n    this.callbacks = callbacks;\n  }\n  get debug() {\n    return !!this.config.debugAdTiming;\n  }\n  // --- Ad stop timer ---\n  scheduleAdStopCountdown(remainingMs) {\n    this.clearAdStopTimer();\n    const ms = Math.max(0, Math.floor(remainingMs));\n    if (ms === 0) {\n      this.ensureAdStoppedByTimer();\n      return;\n    }\n    this.adStopTimerId = window.setTimeout(() => {\n      this.ensureAdStoppedByTimer();\n    }, ms);\n  }\n  clearAdStopTimer() {\n    if (this.adStopTimerId != null) {\n      clearTimeout(this.adStopTimerId);\n      this.adStopTimerId = void 0;\n    }\n  }\n  ensureAdStoppedByTimer() {\n    this.adStopTimerId = void 0;\n    this.callbacks.onAdStopTimerFired();\n  }\n  // --- Ad start timer ---\n  scheduleAdStartIn(delayMs, marker = { type: \"start\" }, cueKey) {\n    this.clearAdStartTimer();\n    const ms = Math.max(0, Math.floor(delayMs));\n    if (ms === 0) {\n      this.callbacks.onAdStartTimerFired(marker, cueKey);\n      return;\n    }\n    this.adStartTimerId = window.setTimeout(() => {\n      this.callbacks.onAdStartTimerFired(marker, cueKey);\n    }, ms);\n  }\n  clearAdStartTimer() {\n    if (this.adStartTimerId != null) {\n      clearTimeout(this.adStartTimerId);\n      this.adStartTimerId = void 0;\n    }\n  }\n  // --- PTS drift ---\n  updatePtsDrift(ptsSecondsSample) {\n    const sampleMs = (this.video.currentTime - ptsSecondsSample) * 1e3;\n    if (!Number.isFinite(sampleMs) || Math.abs(sampleMs) > 6e4) return;\n    const alpha = 0.1;\n    this.ptsDriftEmaMs = this.ptsDriftEmaMs * (1 - alpha) + sampleMs * alpha;\n  }\n  resolveScteBreakStartWallClockMs(marker) {\n    const nowWallClockMs = Date.now();\n    if (typeof marker.ptsSeconds !== \"number\") {\n      return nowWallClockMs;\n    }\n    const nowMs = this.video.currentTime * 1e3;\n    const estimatedCurrentPtsMs = nowMs - this.ptsDriftEmaMs;\n    const deltaMs = marker.ptsSeconds * 1e3 - estimatedCurrentPtsMs;\n    if (!Number.isFinite(deltaMs)) {\n      return nowWallClockMs;\n    }\n    return nowWallClockMs + Math.floor(deltaMs);\n  }\n  // --- Duration boundary ---\n  setAdBreakDurationBoundary(durationMs) {\n    this.expectedAdBreakDurationMs = durationMs;\n    if (durationMs != null && this.currentAdBreakStartWallClockMs != null) {\n      this.scteAdBreakEndWallClockMs = this.currentAdBreakStartWallClockMs + durationMs;\n    } else {\n      this.scteAdBreakEndWallClockMs = void 0;\n    }\n  }\n  scheduleAdStopAtBreakBoundary() {\n    if (this.expectedAdBreakDurationMs == null) {\n      return;\n    }\n    this.scheduleAdStopCountdown(this.getWallClockRemainingAdMs());\n  }\n  // --- Duration budget ---\n  getWallClockRemainingAdMs() {\n    const endWallClockMs = this.getAdBreakEndWallClockMs();\n    if (endWallClockMs != null) {\n      return Math.max(0, endWallClockMs - Date.now());\n    }\n    return 0;\n  }\n  getAdBreakEndWallClockMs() {\n    if (this.scteAdBreakEndWallClockMs != null) {\n      return this.scteAdBreakEndWallClockMs;\n    }\n    if (this.expectedAdBreakDurationMs == null || this.currentAdBreakStartWallClockMs == null) {\n      return void 0;\n    }\n    return this.currentAdBreakStartWallClockMs + this.expectedAdBreakDurationMs;\n  }\n  getDurationBudgetRemainingMs() {\n    if (this.expectedAdBreakDurationMs == null) {\n      return 0;\n    }\n    return Math.max(0, this.expectedAdBreakDurationMs - this.adBreakPlayedDurationMs);\n  }\n  getLoadedAdDurationMs(adController) {\n    const durationSec = adController.getLoadedAdDuration?.();\n    if (durationSec == null || durationSec <= 0) {\n      return 0;\n    }\n    return Math.round(durationSec * 1e3);\n  }\n  adFitsRemainingBudget(durationMs) {\n    if (durationMs <= 0) {\n      return true;\n    }\n    return durationMs <= this.getDurationBudgetRemainingMs();\n  }\n  logAdDurationDecision(accepted, durationMs, adController) {\n    if (!this.debug) {\n      return;\n    }\n    const remainingBudget = this.getDurationBudgetRemainingMs();\n    const adId = adController.getLoadedAdId?.() ?? \"unknown\";\n    if (accepted) {\n      console.log(\n        `[AD-DURATION] Accepted ad id=${adId}, duration=${durationMs}ms, budget remaining after play=${Math.max(0, remainingBudget - durationMs)}ms`\n      );\n    } else {\n      console.log(\n        `[AD-DURATION] Rejected ad id=${adId}, duration=${durationMs}ms exceeds remaining budget=${remainingBudget}ms \\u2014 requesting another ad`\n      );\n    }\n  }\n  recordPlayedAdDuration(adController) {\n    const durationMs = this.getLoadedAdDurationMs(adController);\n    if (durationMs <= 0) {\n      return;\n    }\n    this.adBreakPlayedDurationMs += durationMs;\n    if (this.debug) {\n      console.log(\n        `[AD-DURATION] Played ${durationMs}ms \\u2014 total played=${this.adBreakPlayedDurationMs}ms / ${this.expectedAdBreakDurationMs ?? \"?\"}ms`\n      );\n    }\n  }\n  ensureLoadedAdFitsBudget(adController) {\n    const durationMs = this.getLoadedAdDurationMs(adController);\n    const fits = this.adFitsRemainingBudget(durationMs);\n    this.logAdDurationDecision(fits, durationMs, adController);\n    return fits;\n  }\n  rejectLoadedAdForDuration(adController) {\n    try {\n      adController.destroy();\n    } catch {\n    }\n  }\n  markAdStarted() {\n    this.currentAdIndex++;\n    this.totalAdsInBreak = this.currentAdIndex;\n    this.totalAdRequestsInBreak++;\n    this.lastAdRequestTime = Date.now();\n  }\n  notePodAdStarted() {\n    this.currentAdIndex++;\n    this.totalAdsInBreak = this.currentAdIndex;\n  }\n  getRemainingAdMs() {\n    const wallClockRemaining = this.getWallClockRemainingAdMs();\n    const budgetRemaining = this.getDurationBudgetRemainingMs();\n    if (this.expectedAdBreakDurationMs == null) {\n      return wallClockRemaining;\n    }\n    return Math.min(wallClockRemaining, budgetRemaining);\n  }\n  getMinRemainingMsToStartAd() {\n    const configured = this.config.minRemainingMsToStartAd;\n    if (typeof configured === \"number\" && configured >= 0) {\n      return configured;\n    }\n    return this.defaultMinRemainingMsToStartAd;\n  }\n  hasTimeToStartAnotherAd() {\n    const minRemaining = this.getMinRemainingMsToStartAd();\n    return this.getWallClockRemainingAdMs() > minRemaining && this.getDurationBudgetRemainingMs() > minRemaining;\n  }\n  // --- Circuit breaker ---\n  isTemporaryAdError(error) {\n    const message = error?.message?.toLowerCase() || \"\";\n    if (message.includes(\"no ads available\") || message.includes(\"no fill\") || message.includes(\"nofill\")) {\n      return true;\n    }\n    if (message.includes(\"timeout\")) {\n      return true;\n    }\n    if (message.includes(\"rate limit\") || message.includes(\"too many requests\")) {\n      return true;\n    }\n    if (message.includes(\"ad playback error\")) {\n      return true;\n    }\n    return false;\n  }\n  isUrlInCooldown(vastTagUrl) {\n    const failureTime = this.temporaryFailureUrls.get(vastTagUrl);\n    if (failureTime == null) {\n      return false;\n    }\n    const elapsed = Date.now() - failureTime;\n    if (elapsed >= this.temporaryFailureCooldownMs) {\n      this.temporaryFailureUrls.delete(vastTagUrl);\n      return false;\n    }\n    return true;\n  }\n  cleanupTemporaryFailures() {\n    const now = Date.now();\n    for (const [url, timestamp] of this.temporaryFailureUrls) {\n      if (now - timestamp >= this.temporaryFailureCooldownMs) {\n        this.temporaryFailureUrls.delete(url);\n      }\n    }\n  }\n  isGamInCooldown() {\n    return Date.now() < this.globalNoFillCooldownUntil;\n  }\n  recordGamNoFill() {\n    this.globalConsecutiveNoFills++;\n    if (this.globalConsecutiveNoFills >= this.globalNoFillThreshold) {\n      const exponent = this.globalConsecutiveNoFills - this.globalNoFillThreshold;\n      const backoff = Math.min(\n        this.globalNoFillBackoffBaseMs * Math.pow(2, exponent),\n        this.globalNoFillBackoffMaxMs\n      );\n      this.globalNoFillCooldownUntil = Date.now() + backoff;\n      if (this.debug) {\n        console.log(\n          `[CIRCUIT-BREAKER] GAM cooldown activated: ${backoff}ms (${this.globalConsecutiveNoFills} consecutive no-fills)`\n        );\n      }\n    }\n  }\n  resetGamNoFillCounter() {\n    if (this.globalConsecutiveNoFills > 0 && this.debug) {\n      console.log(\n        `[CIRCUIT-BREAKER] Resetting no-fill counter (was ${this.globalConsecutiveNoFills})`\n      );\n    }\n    this.globalConsecutiveNoFills = 0;\n    this.globalNoFillCooldownUntil = 0;\n  }\n  async enforceGlobalRateLimit() {\n    const now = Date.now();\n    const elapsed = now - this.globalLastGamRequestTime;\n    if (elapsed < this.globalMinGamIntervalMs) {\n      const waitMs = this.globalMinGamIntervalMs - elapsed;\n      if (this.debug) {\n        console.log(`[RATE-LIMIT] Waiting ${waitMs}ms before next GAM request`);\n      }\n      await new Promise((resolve) => setTimeout(resolve, waitMs));\n    }\n    this.globalLastGamRequestTime = Date.now();\n  }\n  // --- Watchdog ---\n  startAdRequestWatchdog(token) {\n    this.clearAdRequestWatchdog();\n    const timeoutMs = this.config.adFailsafeTimeoutMs ?? 1e4;\n    this.adRequestWatchdogToken = token;\n    this.adRequestWatchdogId = window.setTimeout(() => {\n      if (this.adRequestWatchdogToken !== token) {\n        return;\n      }\n      this.adRequestWatchdogId = void 0;\n      this.adRequestWatchdogToken = null;\n      if (this.activeAdRequestToken === token) {\n        this.activeAdRequestToken = null;\n      }\n      this.logAdState(\"ad_request_timeout\", { token, timeoutMs });\n      this.callbacks.onWatchdogTimeout();\n    }, timeoutMs);\n    this.logAdState(\"ad_request_watchdog_started\", { token, timeoutMs });\n  }\n  clearAdRequestWatchdog() {\n    if (this.adRequestWatchdogId != null) {\n      clearTimeout(this.adRequestWatchdogId);\n      this.adRequestWatchdogId = void 0;\n    }\n    if (this.adRequestWatchdogToken != null) {\n      this.logAdState(\"ad_request_watchdog_cleared\", {\n        token: this.adRequestWatchdogToken\n      });\n      this.adRequestWatchdogToken = null;\n    }\n  }\n  // --- Failsafe ---\n  startAdFailsafeTimer(token) {\n    this.clearAdFailsafeTimer();\n    const failsafeMs = this.config.adFailsafeTimeoutMs ?? 1e4;\n    this.adFailsafeToken = token;\n    this.adFailsafeTimerId = window.setTimeout(() => {\n      if (this.adFailsafeToken !== token) {\n        return;\n      }\n      this.adFailsafeTimerId = void 0;\n      this.adFailsafeToken = null;\n      if (this.activeAdRequestToken === token) {\n        this.activeAdRequestToken = null;\n      }\n      this.logAdState(\"ad_failsafe_triggered\", {\n        token,\n        failsafeMs,\n        videoPaused: this.video.paused\n      });\n      this.callbacks.onFailsafeTimeout();\n    }, failsafeMs);\n    this.logAdState(\"ad_failsafe_started\", { token, failsafeMs });\n  }\n  clearAdFailsafeTimer() {\n    if (this.adFailsafeTimerId != null) {\n      clearTimeout(this.adFailsafeTimerId);\n      this.logAdState(\"ad_failsafe_cleared\", { token: this.adFailsafeToken });\n      this.adFailsafeTimerId = void 0;\n    }\n    this.adFailsafeToken = null;\n  }\n  logAdState(event, extra = {}, adPlayer, inAdBreak, showAds) {\n    if (!this.debug) {\n      return;\n    }\n    console.log(\"[StormcloudVideoPlayer][AdState]\", {\n      event,\n      timestamp: (/* @__PURE__ */ new Date()).toISOString(),\n      showAds: showAds ?? false,\n      adPlaying: adPlayer?.isAdPlaying() ?? false,\n      inAdBreak: inAdBreak ?? false,\n      activeAdRequestToken: this.activeAdRequestToken,\n      ...extra\n    });\n  }\n  // --- Reset for ad break end ---\n  resetForBreakEnd() {\n    this.clearAdStopTimer();\n    this.clearAdStartTimer();\n    this.clearAdRequestWatchdog();\n    this.clearAdFailsafeTimer();\n    this.activeAdRequestToken = null;\n    this.expectedAdBreakDurationMs = void 0;\n    this.currentAdBreakStartWallClockMs = void 0;\n    this.scteAdBreakEndWallClockMs = void 0;\n    this.adBreakPlayedDurationMs = 0;\n    this.currentAdIndex = 0;\n    this.totalAdsInBreak = 0;\n    this.consecutiveFailures = 0;\n    this.globalConsecutiveNoFills = 0;\n    this.adBreakEpoch++;\n  }\n  destroy() {\n    this.clearAdStopTimer();\n    this.clearAdStartTimer();\n    this.clearAdFailsafeTimer();\n    this.clearAdRequestWatchdog();\n  }\n};\n\n// src/player/PlaceholderLayer.ts\nvar PlaceholderLayer = class {\n  constructor(video, debug) {\n    this.video = video;\n    this.debug = debug;\n  }\n  ensureContainer() {\n    if (this.container) {\n      return;\n    }\n    const el = document.createElement(\"div\");\n    el.style.position = \"absolute\";\n    el.style.left = \"0\";\n    el.style.top = \"0\";\n    el.style.right = \"0\";\n    el.style.bottom = \"0\";\n    el.style.display = \"none\";\n    el.style.alignItems = \"center\";\n    el.style.justifyContent = \"center\";\n    el.style.pointerEvents = \"none\";\n    el.style.zIndex = \"5\";\n    el.style.backgroundColor = \"#000\";\n    el.style.transition = \"opacity 0.3s ease-in-out\";\n    el.style.opacity = \"0\";\n    if (!this.video.parentElement) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Video element has no parent for placeholder container\");\n      }\n      return;\n    }\n    this.video.parentElement.appendChild(el);\n    this.container = el;\n  }\n  show() {\n    this.ensureContainer();\n    if (!this.container) {\n      return;\n    }\n    if (!this.video.muted) {\n      this.video.muted = true;\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Muted video when showing placeholder\");\n      }\n    }\n    const wasHidden = this.container.style.display === \"none\" || this.container.style.opacity === \"0\";\n    if (wasHidden) {\n      this.container.style.transition = \"none\";\n    } else {\n      this.container.style.transition = \"opacity 0.3s ease-in-out\";\n    }\n    this.container.style.backgroundColor = \"#000\";\n    this.container.style.display = \"flex\";\n    this.container.offsetHeight;\n    this.container.style.opacity = \"1\";\n    this.container.style.pointerEvents = \"auto\";\n    if (wasHidden) {\n      requestAnimationFrame(() => {\n        if (this.container) {\n          this.container.style.transition = \"opacity 0.3s ease-in-out\";\n        }\n      });\n    }\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Showing placeholder layer (between content and ad layer)\");\n    }\n  }\n  hide() {\n    if (!this.container) {\n      return;\n    }\n    this.container.style.opacity = \"0\";\n    setTimeout(() => {\n      if (this.container) {\n        this.container.style.display = \"none\";\n        this.container.style.pointerEvents = \"none\";\n        this.container.style.backgroundColor = \"#000\";\n      }\n    }, 300);\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Hiding placeholder layer\");\n    }\n  }\n  destroy() {\n    if (this.container) {\n      if (this.container.parentElement) {\n        this.container.parentElement.removeChild(this.container);\n      }\n      this.container = void 0;\n    }\n  }\n};\n\n// src/player/HlsEngine.ts\nvar import_hls2 = __toESM(require(\"hls.js\"), 1);\nvar HlsEngine = class {\n  constructor(config, video, cueManager, timing, callbacks) {\n    this.isLiveStream = false;\n    this.nativeHlsMode = false;\n    this.videoSrcProtection = null;\n    this.reloadingLiveStream = false;\n    this.bufferedSegmentsCount = 0;\n    this.shouldAutoplayAfterBuffering = false;\n    this.hasInitialBufferCompleted = false;\n    this.config = config;\n    this.video = video;\n    this.cueManager = cueManager;\n    this.timing = timing;\n    this.callbacks = callbacks;\n  }\n  get debug() {\n    return !!this.config.debugAdTiming;\n  }\n  shouldUseNativeHls(getStreamType) {\n    const streamType = getStreamType();\n    if (streamType === \"other\") {\n      return true;\n    }\n    const canNative = this.video.canPlayType(\"application/vnd.apple.mpegurl\");\n    return !!(this.config.allowNativeHls && canNative);\n  }\n  async setupNativeHls() {\n    this.nativeHlsMode = true;\n    this.videoSrcProtection = this.config.src;\n    this.video.src = this.config.src;\n    this.isLiveStream = this.config.isLiveStream ?? (this.config.lowLatencyMode ?? false);\n    if (this.debug) {\n      const adBehavior = this.isLiveStream ? \"live (main video continues muted during ads)\" : \"vod (main video pauses during ads)\";\n      console.log(\n        \"[StormcloudVideoPlayer] Using native HLS playback:\",\n        {\n          isLive: this.isLiveStream,\n          allowNativeHls: this.config.allowNativeHls,\n          adBehavior\n        }\n      );\n    }\n    if (this.config.autoplay) {\n      await this.video.play()?.catch(() => {\n      });\n    }\n  }\n  setupHls() {\n    this.hls = new import_hls2.default({\n      enableWorker: true,\n      backBufferLength: 30,\n      liveDurationInfinity: true,\n      lowLatencyMode: !!this.config.lowLatencyMode,\n      maxLiveSyncPlaybackRate: this.config.lowLatencyMode ? 1.5 : 1,\n      ...this.config.lowLatencyMode ? { liveSyncDuration: 2 } : {},\n      maxBufferLength: 30,\n      maxMaxBufferLength: 600,\n      maxBufferSize: 60 * 1e3 * 1e3,\n      maxBufferHole: 0.5,\n      highBufferWatchdogPeriod: 2,\n      nudgeOffset: 0.1,\n      nudgeMaxRetry: 3,\n      startPosition: -1\n    });\n    this.hls.on(import_hls2.default.Events.MEDIA_ATTACHED, () => {\n      this.hls?.loadSource(this.config.src);\n    });\n    this.hls.on(import_hls2.default.Events.MANIFEST_PARSED, async (_, _data) => {\n      this.isLiveStream = this.config.isLiveStream ?? (this.hls?.levels?.some(\n        (level) => level?.details?.live === true || level?.details?.type === \"LIVE\"\n      ) ?? false);\n      await this.callbacks.onManifestParsed(this.isLiveStream);\n      this.bufferedSegmentsCount = 0;\n      this.hasInitialBufferCompleted = false;\n      this.shouldAutoplayAfterBuffering = !!this.config.autoplay;\n      const minSegments = this.config.minSegmentsBeforePlay ?? 2;\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Waiting for\",\n          minSegments,\n          \"segments to buffer before playback\"\n        );\n      }\n      if (minSegments === 0 || !this.config.autoplay) {\n        this.hasInitialBufferCompleted = true;\n        if (this.config.autoplay) {\n          await this.video.play()?.catch(() => {\n          });\n        }\n      }\n      this.reloadingLiveStream = false;\n    });\n    this.hls.on(import_hls2.default.Events.LEVEL_LOADED, (_evt, data) => {\n      if (this.callbacks.isInAdBreak() || this.callbacks.hasPendingAdBreak()) {\n        return;\n      }\n      const details = data?.details;\n      if (!details || !details.fragments || details.fragments.length === 0) {\n        return;\n      }\n      const fragmentsToScan = Math.min(5, details.fragments.length);\n      for (let i = 0; i < fragmentsToScan; i++) {\n        const frag = details.fragments[i];\n        const tagList = frag?.tagList;\n        if (!Array.isArray(tagList)) continue;\n        for (const entry of tagList) {\n          let tag = \"\";\n          let value = \"\";\n          if (Array.isArray(entry)) {\n            tag = String(entry[0] ?? \"\");\n            value = String(entry[1] ?? \"\");\n          } else if (typeof entry === \"string\") {\n            const idx = entry.indexOf(\":\");\n            if (idx >= 0) {\n              tag = entry.substring(0, idx);\n              value = entry.substring(idx + 1);\n            } else {\n              tag = entry;\n            }\n          }\n          if (!tag) continue;\n          if (tag.includes(\"EXT-X-CUE-OUT\") || tag.includes(\"EXT-X-DATERANGE\")) {\n            const attrs = tag.includes(\"EXT-X-DATERANGE\") ? parseAttributeList(value) : {};\n            const hasScteOut = tag.includes(\"EXT-X-CUE-OUT\") || \"SCTE35-OUT\" in attrs || attrs[\"SCTE35-OUT\"] !== void 0;\n            if (hasScteOut) {\n              const durationSeconds = parseCueOutDuration(value);\n              const marker = {\n                type: \"start\",\n                ...durationSeconds !== void 0 ? { durationSeconds } : {},\n                raw: { tag, value, earlyDetection: true }\n              };\n              if (this.debug) {\n                console.log(\"[StormcloudVideoPlayer] EARLY SCTE-35 DETECTION: Ad break marker found in fragment\", i, \"- starting pre-fetch (NOT playing yet)\");\n              }\n              this.callbacks.onScte35Cue(marker, {\n                ...this.cueManager.createScte35CueContext(\"manifest\", \"early\", frag)\n              });\n              return;\n            }\n          }\n        }\n      }\n    });\n    this.hls.on(import_hls2.default.Events.FRAG_BUFFERED, async (_evt, _data) => {\n      if (this.hasInitialBufferCompleted) {\n        return;\n      }\n      this.bufferedSegmentsCount++;\n      const minSegments = this.config.minSegmentsBeforePlay ?? 2;\n      if (this.debug) {\n        console.log(\n          `[StormcloudVideoPlayer] Buffered segment ${this.bufferedSegmentsCount}/${minSegments}`\n        );\n      }\n      if (this.bufferedSegmentsCount >= minSegments) {\n        this.hasInitialBufferCompleted = true;\n        if (this.shouldAutoplayAfterBuffering) {\n          if (this.debug) {\n            console.log(\n              `[StormcloudVideoPlayer] Initial buffer complete (${this.bufferedSegmentsCount} segments). Starting playback.`\n            );\n          }\n          await this.video.play()?.catch((err) => {\n            if (this.debug) {\n              console.warn(\"[StormcloudVideoPlayer] Autoplay failed:\", err);\n            }\n          });\n        }\n      }\n    });\n    this.hls.on(import_hls2.default.Events.FRAG_PARSING_METADATA, (_evt, data) => {\n      const id3Tags = (data?.samples || []).map((s) => ({\n        key: \"ID3\",\n        value: s?.data,\n        ptsSeconds: s?.pts\n      }));\n      id3Tags.forEach((tag) => this.onId3Tag(tag));\n    });\n    this.hls.on(import_hls2.default.Events.FRAG_LOADED, (_evt, data) => {\n      this.processFragmentScte35Payload(\n        data?.payload,\n        typeof data?.frag?.sn === \"number\" ? data.frag.sn : void 0,\n        getFragmentStartSeconds(data?.frag)\n      );\n    });\n    this.hls.on(import_hls2.default.Events.FRAG_DECRYPTED, (_evt, data) => {\n      this.processFragmentScte35Payload(\n        data?.payload,\n        typeof data?.frag?.sn === \"number\" ? data.frag.sn : void 0,\n        getFragmentStartSeconds(data?.frag)\n      );\n    });\n    this.hls.on(import_hls2.default.Events.FRAG_CHANGED, (_evt, data) => {\n      const frag = data?.frag;\n      const tagList = frag?.tagList;\n      if (!Array.isArray(tagList)) {\n        this.callbacks.activatePendingCuesForFragment(frag);\n        return;\n      }\n      for (const entry of tagList) {\n        let tag = \"\";\n        let value = \"\";\n        if (Array.isArray(entry)) {\n          tag = String(entry[0] ?? \"\");\n          value = String(entry[1] ?? \"\");\n        } else if (typeof entry === \"string\") {\n          const idx = entry.indexOf(\":\");\n          if (idx >= 0) {\n            tag = entry.substring(0, idx);\n            value = entry.substring(idx + 1);\n          } else {\n            tag = entry;\n            value = \"\";\n          }\n        }\n        if (!tag) continue;\n        if (tag.includes(\"EXT-X-CUE-OUT-CONT\")) {\n          const prog = parseCueOutCont(value);\n          const marker = {\n            type: \"progress\",\n            ...prog?.duration !== void 0 ? { durationSeconds: prog.duration } : {},\n            ...prog?.elapsed !== void 0 ? { ptsSeconds: prog.elapsed } : {},\n            raw: { tag, value }\n          };\n          this.callbacks.onScte35Cue(marker, {\n            ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag)\n          });\n        } else if (tag.includes(\"EXT-X-CUE-OUT\")) {\n          const durationSeconds = parseCueOutDuration(value);\n          const marker = {\n            type: \"start\",\n            ...durationSeconds !== void 0 ? { durationSeconds } : {},\n            raw: { tag, value }\n          };\n          this.callbacks.onScte35Cue(marker, {\n            ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag)\n          });\n        } else if (tag.includes(\"EXT-X-CUE-IN\")) {\n          this.callbacks.onScte35Cue(\n            { type: \"end\", raw: { tag, value } },\n            {\n              ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag)\n            }\n          );\n        } else if (tag.includes(\"EXT-X-DATERANGE\")) {\n          const attrs = parseAttributeList(value);\n          const hasScteOut = \"SCTE35-OUT\" in attrs || attrs[\"SCTE35-OUT\"] !== void 0;\n          const hasScteIn = \"SCTE35-IN\" in attrs || attrs[\"SCTE35-IN\"] !== void 0;\n          const klass = String(attrs[\"CLASS\"] ?? \"\");\n          const duration = toNumber(attrs[\"DURATION\"]);\n          if (hasScteOut || /com\\.apple\\.hls\\.cue/i.test(klass)) {\n            const marker = {\n              type: \"start\",\n              ...duration !== void 0 ? { durationSeconds: duration } : {},\n              raw: { tag, value, attrs }\n            };\n            this.callbacks.onScte35Cue(marker, {\n              ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag)\n            });\n          }\n          if (hasScteIn) {\n            this.callbacks.onScte35Cue(\n              { type: \"end\", raw: { tag, value, attrs } },\n              {\n                ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag)\n              }\n            );\n          }\n        }\n      }\n      this.callbacks.activatePendingCuesForFragment(frag);\n    });\n    this.hls.on(import_hls2.default.Events.ERROR, (_evt, data) => {\n      if (data?.fatal) {\n        switch (data.type) {\n          case import_hls2.default.ErrorTypes.NETWORK_ERROR:\n            this.hls?.startLoad();\n            break;\n          case import_hls2.default.ErrorTypes.MEDIA_ERROR:\n            this.hls?.recoverMediaError();\n            break;\n          default:\n            this.callbacks.onFatalDestroy();\n            break;\n        }\n      }\n    });\n    this.hls.attachMedia(this.video);\n  }\n  onId3Tag(tag) {\n    if (typeof tag.ptsSeconds === \"number\") {\n      this.timing.updatePtsDrift(tag.ptsSeconds);\n    }\n    const marker = parseScte35FromId3(tag);\n    if (marker) {\n      this.callbacks.onScte35Cue(marker, {\n        source: \"id3\",\n        readiness: \"playback\"\n      });\n    }\n  }\n  processFragmentScte35Payload(payloadData, fragmentSn, fragmentStartSeconds) {\n    const payload = normalizeFragmentPayload(payloadData);\n    if (!payload) {\n      return;\n    }\n    const markers = parseScte35FromTsPackets(\n      payload,\n      this.cueManager.tsScte35Pids,\n      this.cueManager.pmtPids,\n      this.cueManager.processedTsScte35Sections\n    );\n    markers.forEach((marker) => {\n      const context = {\n        source: \"ts\",\n        readiness: \"early\"\n      };\n      if (fragmentSn !== void 0) {\n        context.fragmentSn = fragmentSn;\n      }\n      if (fragmentStartSeconds !== void 0) {\n        context.fragmentStartSeconds = fragmentStartSeconds;\n      }\n      this.callbacks.onScte35Cue(marker, context);\n    });\n  }\n  getLiveSyncPosition() {\n    const pos = this.hls?.liveSyncPosition;\n    return typeof pos === \"number\" && Number.isFinite(pos) ? pos : void 0;\n  }\n  restartLoadAt(position) {\n    if (!this.hls) {\n      return;\n    }\n    try {\n      this.hls.stopLoad();\n      this.hls.startLoad(position);\n    } catch (error) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to restart HLS load at live edge:\", error);\n      }\n    }\n  }\n  recoverMediaError() {\n    if (!this.hls) {\n      return;\n    }\n    try {\n      this.hls.recoverMediaError();\n    } catch (error) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] recoverMediaError() failed:\", error);\n      }\n    }\n  }\n  reloadLiveStream() {\n    const hls = this.hls;\n    if (!hls) {\n      return;\n    }\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Hard-reloading live stream (detach \\u2192 reset video \\u2192 re-attach)\");\n    }\n    try {\n      this.reloadingLiveStream = true;\n      hls.stopLoad();\n      hls.detachMedia();\n      try {\n        this.video.removeAttribute(\"src\");\n        this.video.load();\n      } catch (error) {\n        console.warn(\"[StormcloudVideoPlayer] video.load() threw after src removal:\", error);\n      }\n      hls.attachMedia(this.video);\n    } catch (error) {\n      this.reloadingLiveStream = false;\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to hard-reload live stream:\", error);\n      }\n    }\n  }\n  destroy() {\n    this.hls?.destroy();\n    this.hls = void 0;\n  }\n};\n\n// src/player/PlayerControls.ts\nfunction getAdAudioVolume(adPlayer) {\n  return adPlayer.getOriginalMutedState() ? 0 : adPlayer.getOriginalVolume();\n}\nfunction toggleMute(video, adPlayer, debug) {\n  if (adPlayer.isAdPlaying()) {\n    const newMutedState = !adPlayer.getOriginalMutedState();\n    const restoreVolume = adPlayer.getOriginalVolume() || 1;\n    adPlayer.updateOriginalMutedState(newMutedState, video.volume);\n    adPlayer.setAdVolume(newMutedState ? 0 : restoreVolume);\n    if (debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Mute toggle during ad - immediately applied:\",\n        newMutedState\n      );\n    }\n  } else {\n    video.muted = !video.muted;\n    adPlayer.updateOriginalMutedState(video.muted, video.volume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] Muted:\", video.muted);\n    }\n  }\n}\nfunction toggleFullscreen(video, debug) {\n  return new Promise((resolve, reject) => {\n    if (!document.fullscreenElement) {\n      const container = video.parentElement;\n      if (!container) {\n        reject(new Error(\"No parent container found for fullscreen\"));\n        return;\n      }\n      container.requestFullscreen().then(() => {\n        if (debug) {\n          console.log(\"[StormcloudVideoPlayer] Entered fullscreen\");\n        }\n        resolve();\n      }).catch((err) => {\n        if (debug) {\n          console.error(\"[StormcloudVideoPlayer] Fullscreen error:\", err);\n        }\n        reject(err);\n      });\n    } else {\n      document.exitFullscreen().then(() => {\n        if (debug) {\n          console.log(\"[StormcloudVideoPlayer] Exited fullscreen\");\n        }\n        resolve();\n      }).catch((err) => {\n        if (debug) {\n          console.error(\n            \"[StormcloudVideoPlayer] Exit fullscreen error:\",\n            err\n          );\n        }\n        reject(err);\n      });\n    }\n  });\n}\nfunction isMuted(video, adPlayer) {\n  if (adPlayer.isAdPlaying()) {\n    return adPlayer.getOriginalMutedState();\n  }\n  return video.muted;\n}\nfunction setMuted(video, adPlayer, muted, debug) {\n  const adPlaying = adPlayer.isAdPlaying();\n  if (adPlaying && muted === video.muted) {\n    if (debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] setMuted reflective update during ad ignored\",\n        { muted }\n      );\n    }\n    return;\n  }\n  video.muted = muted;\n  if (adPlaying) {\n    adPlayer.updateOriginalMutedState(muted, video.volume);\n    adPlayer.setAdVolume(muted ? 0 : 1);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setMuted applied during ad\", {\n        muted\n      });\n    }\n    return;\n  }\n  adPlayer.updateOriginalMutedState(muted, video.volume);\n  if (debug) {\n    console.log(\"[StormcloudVideoPlayer] setMuted called:\", muted);\n  }\n}\nfunction setVolume(video, adPlayer, volume, debug) {\n  const clampedVolume = Math.max(0, Math.min(1, volume));\n  const adPlaying = adPlayer.isAdPlaying();\n  if (adPlaying) {\n    adPlayer.setAdVolume(clampedVolume);\n    adPlayer.updateOriginalMutedState(clampedVolume === 0, clampedVolume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setVolume applied during ad\", {\n        volume: clampedVolume\n      });\n    }\n  } else {\n    video.volume = clampedVolume;\n    video.muted = clampedVolume === 0;\n    adPlayer.updateOriginalMutedState(clampedVolume === 0, clampedVolume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setVolume called:\", clampedVolume);\n    }\n  }\n}\nfunction getVolume(video, adPlayer) {\n  const adPlaying = adPlayer.isAdPlaying();\n  if (adPlaying) {\n    return adPlayer.getAdVolume();\n  }\n  return video.volume;\n}\nfunction isFullscreen() {\n  return !!document.fullscreenElement;\n}\nfunction resizePlayer(video, adPlayer, debug) {\n  if (debug) {\n    console.log(\"[StormcloudVideoPlayer] Resizing player\");\n  }\n  if (adPlayer && adPlayer.isAdPlaying()) {\n    const width = video.clientWidth || 640;\n    const height = video.clientHeight || 480;\n    if (debug) {\n      console.log(\n        `[StormcloudVideoPlayer] Resizing ads manager to ${width}x${height}`\n      );\n    }\n    adPlayer.resize(width, height);\n  }\n}\n\n// src/player/AdBreakOrchestrator.ts\nvar AdBreakOrchestrator = class {\n  constructor(host, timing, adConfig, cueManager, placeholder) {\n    this.inAdBreak = false;\n    this.showAds = false;\n    this.isShowingPlaceholder = false;\n    this.adDetectSentForCurrentBreak = false;\n    this.continuousFetchingActive = false;\n    this.continuousFetchLoopRunning = false;\n    this.adRequestQueue = [];\n    this.adPodQueue = [];\n    this.maxPlaceholderDurationMs = 5e3;\n    this.pendingAdBreak = null;\n    this.host = host;\n    this.timing = timing;\n    this.adConfig = adConfig;\n    this.cueManager = cueManager;\n    this.placeholder = placeholder;\n  }\n  get debug() {\n    return !!this.host.config.debugAdTiming;\n  }\n  get analyticsContext() {\n    return buildAnalyticsContext(this.host.config);\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  IMA event listeners\n  // ───────────────────────────────────────────────────────────────\n  nextAdRequestUrl(baseVastUrl) {\n    const remaining = Math.min(\n      this.timing.getWallClockRemainingAdMs(),\n      this.timing.getDurationBudgetRemainingMs()\n    );\n    const breakDurationMs = remaining > 0 ? remaining : void 0;\n    return this.host.generatePodVastUrl(baseVastUrl, breakDurationMs);\n  }\n  attachImaEventListeners() {\n    const adPlayer = this.host.getAdPlayer();\n    adPlayer.on(\"pod_ad_started\", (payload) => {\n      this.timing.notePodAdStarted();\n      if (this.debug) {\n        console.log(\n          `[POD] Playing pod ad ${payload?.index != null ? payload.index + 1 : \"?\"}/${payload?.total ?? \"?\"}`\n        );\n      }\n    });\n    adPlayer.on(\"all_ads_completed\", () => {\n      sendAdImpressionTracking(\n        this.host.config.licenseKey,\n        { source: \"hls\", adIndex: this.timing.currentAdIndex, timestamp: (/* @__PURE__ */ new Date()).toISOString() },\n        this.analyticsContext\n      ).catch(() => {\n      });\n      this.timing.recordPlayedAdDuration(this.host.getAdPlayer());\n      const remaining = this.timing.getRemainingAdMs();\n      this.timing.consecutiveFailures = 0;\n      if (this.debug) {\n        console.log(\n          `[StormcloudVideoPlayer] all_ads_completed event received - remaining=${remaining}ms, queued ads=${this.adRequestQueue.length}`,\n          this.adRequestQueue.length > 0 ? { queuedUrls: [...this.adRequestQueue] } : {}\n        );\n      }\n      if (this.inAdBreak) {\n        if (this.timing.hasTimeToStartAnotherAd()) {\n          this.tryNextAvailableAdWithRateLimit();\n        } else {\n          this.handleAdPodComplete();\n        }\n      }\n    });\n    adPlayer.on(\"ad_error\", (errorPayload) => {\n      let errorMessage = \"Ad playback failed\";\n      if (errorPayload) {\n        const errorCode = errorPayload.code || errorPayload.errorCode || \"unknown\";\n        const vastErrorCode = errorPayload.vastErrorCode;\n        const message = errorPayload.message || errorPayload.errorMessage || \"Unknown error\";\n        const cause = errorPayload.cause || errorPayload.innerError || errorPayload.error;\n        errorMessage = `Ad error: AdError ${errorCode}: ${message}`;\n        if (vastErrorCode && vastErrorCode !== \"N/A\" && vastErrorCode !== errorCode) {\n          errorMessage += ` (VAST Error Code: ${vastErrorCode})`;\n        }\n        if (cause) {\n          const causeMessage = typeof cause === \"string\" ? cause : cause.message || String(cause);\n          errorMessage += `. Caused by: ${causeMessage}`;\n        }\n      }\n      console.error(\"[AD-ERROR]\", errorMessage, errorPayload || \"\");\n      this.handleAdFailure();\n    });\n    adPlayer.on(\"content_pause\", () => {\n      this.timing.clearAdFailsafeTimer();\n      this.timing.clearAdRequestWatchdog();\n      this.timing.activeAdRequestToken = null;\n      this.showAds = true;\n      this.timing.resetGamNoFillCounter();\n      if (this.inAdBreak && this.timing.expectedAdBreakDurationMs != null && this.timing.getAdBreakEndWallClockMs() == null) {\n        this.timing.scheduleAdStopAtBreakBoundary();\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] Starting ad break timer on content_pause (first ad starting)\");\n        }\n      }\n      this.host.getAdPlayer().setAdVolume(getAdAudioVolume(this.host.getAdPlayer()));\n      if (this.isShowingPlaceholder) {\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] Hiding placeholder - new ads starting\");\n        }\n        this.host.getAdPlayer().hidePlaceholder();\n        this.isShowingPlaceholder = false;\n      }\n    });\n    adPlayer.on(\"content_resume\", () => {\n      sendAdImpressionTracking(\n        this.host.config.licenseKey,\n        { source: \"hls\", adIndex: this.timing.currentAdIndex, timestamp: (/* @__PURE__ */ new Date()).toISOString() },\n        this.analyticsContext\n      ).catch(() => {\n      });\n      if (!this.host.video.muted) {\n        this.host.video.muted = true;\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] Muted video on content_resume (ad ended, gap between ads)\");\n        }\n      }\n      this.timing.clearAdFailsafeTimer();\n      this.timing.clearAdRequestWatchdog();\n      this.timing.activeAdRequestToken = null;\n      this.showAds = false;\n      if (!this.inAdBreak) {\n        return;\n      }\n      this.timing.consecutiveFailures = 0;\n      this.timing.recordPlayedAdDuration(this.host.getAdPlayer());\n      const remaining = this.timing.getRemainingAdMs();\n      if (this.debug) {\n        console.log(\n          `[CONTINUOUS-FETCH] content_resume event: remaining=${remaining}ms, queued ads=${this.adRequestQueue.length}`,\n          this.adRequestQueue.length > 0 ? { queuedUrls: [...this.adRequestQueue] } : {}\n        );\n      }\n      if (this.timing.hasTimeToStartAnotherAd()) {\n        this.tryNextAvailableAdWithRateLimit();\n      } else {\n        this.handleAdPodComplete();\n      }\n    });\n  }\n  recreateAdController() {\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Recreating AdController for new ad\");\n    }\n    const shouldShowPlaceholder = this.inAdBreak && this.showAds;\n    const adPlayer = this.host.getAdPlayer();\n    if (shouldShowPlaceholder && adPlayer) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Showing placeholder before destroying old AdController\");\n      }\n      this.placeholder.show();\n      adPlayer.showPlaceholder();\n      this.isShowingPlaceholder = true;\n    }\n    const preservedMutedState = adPlayer.getOriginalMutedState();\n    const preservedVolumeState = adPlayer.getOriginalVolume();\n    if (adPlayer) {\n      try {\n        adPlayer.destroy();\n        this.host.video.muted = true;\n      } catch (error) {\n        if (this.debug) {\n          console.warn(\"[StormcloudVideoPlayer] Error destroying old AdController:\", error);\n        }\n      }\n    }\n    const continueLiveStreamDuringAds = this.host.shouldContinueLiveStreamDuringAds();\n    const newAdPlayer = this.host.createAdPlayer(continueLiveStreamDuringAds);\n    this.host.setAdPlayer(newAdPlayer);\n    newAdPlayer.initialize();\n    newAdPlayer.updateOriginalMutedState(preservedMutedState, preservedVolumeState);\n    this.attachImaEventListeners();\n    if (shouldShowPlaceholder) {\n      this.placeholder.show();\n      newAdPlayer.showPlaceholder();\n      this.isShowingPlaceholder = true;\n    }\n  }\n  clearPendingAdBreak() {\n    if (this.prefetchTimerId != null) {\n      clearTimeout(this.prefetchTimerId);\n      this.prefetchTimerId = void 0;\n    }\n    this.pendingAdBreak = null;\n    this.cueManager.pendingScte35CueKey = void 0;\n    this.adConfig.podAssignedByPrefetch = false;\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Ad break start\n  // ───────────────────────────────────────────────────────────────\n  async handleAdStart(_marker) {\n    const scheduled = this.adConfig.findCurrentOrNextBreak(\n      this.host.video.currentTime * 1e3\n    );\n    if (scheduled) {\n      this.adConfig.consumedVmapBreakIds.add(this.adConfig.getAdBreakKey(scheduled));\n    }\n    const tags = this.adConfig.selectVastTagsForBreak(scheduled);\n    let baseVastUrl;\n    if (tags && tags.length > 0 && tags[0]) {\n      baseVastUrl = tags[0];\n    } else if (this.adConfig.apiVastTagUrl) {\n      baseVastUrl = this.adConfig.apiVastTagUrl;\n    } else {\n      this.clearPendingAdBreak();\n      return;\n    }\n    const adBreakDurationMs = _marker.durationSeconds != null ? _marker.durationSeconds * 1e3 : scheduled?.durationMs;\n    if (this.debug) {\n      const mode = this.host.config.isLiveStream ? \"LIVE\" : \"VOD\";\n      console.log(\n        `[CONTINUOUS-FETCH] ${mode} MODE: Target duration=${adBreakDurationMs}ms`\n      );\n    }\n    this.timing.failedVastUrls.clear();\n    this.timing.temporaryFailureUrls.clear();\n    this.timing.consecutiveFailures = 0;\n    this.continuousFetchingActive = true;\n    this.isShowingPlaceholder = false;\n    this.timing.totalAdRequestsInBreak = 0;\n    if (this.adConfig.podAssignedByPrefetch) {\n      this.adConfig.podAssignedByPrefetch = false;\n    } else {\n      this.adConfig.beginNewAdPod();\n    }\n    const currentMuted = this.host.video.muted;\n    const currentVolume = this.host.video.volume;\n    this.host.getAdPlayer().updateOriginalMutedState(currentMuted, currentVolume);\n    this.inAdBreak = true;\n    this.timing.adBreakPlayedDurationMs = 0;\n    this.timing.currentAdIndex = 0;\n    this.timing.totalAdsInBreak = 0;\n    this.adPodQueue = [];\n    this.showAds = false;\n    if (this.timing.expectedAdBreakDurationMs == null && adBreakDurationMs != null) {\n      this.timing.expectedAdBreakDurationMs = adBreakDurationMs;\n    }\n    const podPlayed = await this.startOptimizedPod(\n      baseVastUrl,\n      adBreakDurationMs,\n      currentMuted,\n      currentVolume\n    );\n    if (!podPlayed) {\n      if (this.debug) {\n        console.log(\"[POD] Initial pod request did not fill; attempting top-up pod request\");\n      }\n      this.continuousFetchingActive = true;\n      this.startContinuousFetching(baseVastUrl);\n      await this.tryNextAvailableAdWithRateLimit();\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Optimized pod (single multi-ad request)\n  // ───────────────────────────────────────────────────────────────\n  async startOptimizedPod(baseVastUrl, breakDurationMs, currentMuted, currentVolume) {\n    let podUrl;\n    if (this.pendingAdBreak && this.pendingAdBreak.vastUrls.length > 0) {\n      podUrl = this.pendingAdBreak.vastUrls[0];\n      this.clearPendingAdBreak();\n    } else {\n      podUrl = this.host.generatePodVastUrl(baseVastUrl, breakDurationMs);\n    }\n    if (!podUrl) {\n      return false;\n    }\n    this.continuousFetchingActive = false;\n    this.recreateAdController();\n    const adPlayer = this.host.getAdPlayer();\n    const requestToken = ++this.timing.adRequestTokenCounter;\n    this.timing.activeAdRequestToken = requestToken;\n    this.timing.startAdRequestWatchdog(requestToken);\n    try {\n      await this.timing.enforceGlobalRateLimit();\n      this.timing.lastAdRequestTime = Date.now();\n      await adPlayer.requestAds(podUrl);\n      this.timing.clearAdRequestWatchdog();\n      if (this.timing.activeAdRequestToken !== requestToken) {\n        return true;\n      }\n      const podCount = adPlayer.getPodAdCount?.() ?? 1;\n      if (podCount < 1) {\n        return false;\n      }\n      if (this.debug) {\n        console.log(\n          podCount === 1 ? \"[POD] Response contained a single ad; playing it and enabling pod top-up\" : `[POD] Optimized pod returned ${podCount} ads; playing pod in one controller`\n        );\n      }\n      sendAdLoadedTracking(\n        this.host.config.licenseKey,\n        { source: \"hls\", vastUrl: podUrl, timestamp: (/* @__PURE__ */ new Date()).toISOString() },\n        this.analyticsContext\n      ).catch(() => {\n      });\n      this.timing.startAdFailsafeTimer(requestToken);\n      await adPlayer.play();\n      this.timing.markAdStarted();\n      if (this.timing.expectedAdBreakDurationMs != null && this.timing.getAdBreakEndWallClockMs() == null) {\n        this.timing.scheduleAdStopAtBreakBoundary();\n      }\n      adPlayer.setAdVolume(currentMuted ? 0 : currentVolume);\n      this.timing.consecutiveFailures = 0;\n      this.continuousFetchingActive = true;\n      this.startContinuousFetching(baseVastUrl);\n      return true;\n    } catch (error) {\n      this.timing.clearAdRequestWatchdog();\n      this.timing.clearAdFailsafeTimer();\n      if (this.timing.activeAdRequestToken === requestToken) {\n        this.timing.activeAdRequestToken = null;\n      }\n      if (this.debug) {\n        console.warn(\"[POD] Optimized pod request/play failed:\", error);\n      }\n      if (this.timing.isTemporaryAdError(error)) {\n        this.timing.temporaryFailureUrls.set(podUrl, Date.now());\n      }\n      this.continuousFetchingActive = true;\n      this.recreateAdController();\n      return false;\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Continuous fetching\n  // ───────────────────────────────────────────────────────────────\n  startContinuousFetching(baseVastUrl) {\n    if (!this.continuousFetchingActive) {\n      return;\n    }\n    if (this.continuousFetchLoopRunning) {\n      if (this.debug) {\n        console.log(\"[CONTINUOUS-FETCH] Fetch loop already running, skipping duplicate start\");\n      }\n      return;\n    }\n    if (this.debug) {\n      console.log(\"[CONTINUOUS-FETCH] Starting continuous ad fetching loop\");\n    }\n    this.continuousFetchLoopRunning = true;\n    this.continuousFetchLoop(baseVastUrl);\n  }\n  async continuousFetchLoop(baseVastUrl) {\n    const epoch = this.timing.adBreakEpoch;\n    while (this.continuousFetchingActive && this.inAdBreak && epoch === this.timing.adBreakEpoch) {\n      const remaining = Math.min(\n        this.timing.getWallClockRemainingAdMs(),\n        this.timing.getDurationBudgetRemainingMs()\n      );\n      if (remaining <= this.timing.getMinRemainingMsToStartAd()) {\n        if (this.debug) {\n          console.log(`[CONTINUOUS-FETCH] Not enough ad break time left (wall=${this.timing.getWallClockRemainingAdMs()}ms, budget=${this.timing.getDurationBudgetRemainingMs()}ms), stopping URL generation`);\n        }\n        break;\n      }\n      if (this.timing.isGamInCooldown()) {\n        if (this.debug) {\n          console.log(\"[CIRCUIT-BREAKER] GAM in cooldown, stopping URL generation\");\n        }\n        break;\n      }\n      if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n        if (this.debug) {\n          console.log(`[CONTINUOUS-FETCH] Too many consecutive failures (${this.timing.consecutiveFailures}), stopping URL generation`);\n        }\n        break;\n      }\n      if (this.timing.totalAdRequestsInBreak >= this.timing.maxTotalAdRequestsPerBreak) {\n        if (this.debug) {\n          console.log(`[CONTINUOUS-FETCH] Maximum ad requests reached (${this.timing.maxTotalAdRequestsPerBreak}), stopping`);\n        }\n        break;\n      }\n      const maxQueueSize = 5;\n      if (this.adRequestQueue.length >= maxQueueSize) {\n        if (this.debug) {\n          console.log(`[CONTINUOUS-FETCH] URL queue full (${this.adRequestQueue.length}), waiting...`);\n        }\n        await new Promise((resolve) => setTimeout(resolve, 1e3));\n        continue;\n      }\n      const newAdUrl = this.nextAdRequestUrl(baseVastUrl);\n      if (!newAdUrl || this.timing.failedVastUrls.has(newAdUrl) || this.timing.isUrlInCooldown(newAdUrl)) {\n        await new Promise((resolve) => setTimeout(resolve, 500));\n        continue;\n      }\n      if (this.debug) {\n        const queuedUrlsPreview = [...this.adRequestQueue, newAdUrl];\n        console.log(\n          `[CONTINUOUS-FETCH] Queued VAST URL (queue size: ${queuedUrlsPreview.length})`,\n          { queuedUrls: queuedUrlsPreview }\n        );\n      }\n      this.adRequestQueue.push(newAdUrl);\n      const generationDelay = this.timing.consecutiveFailures > 0 ? Math.min(1e3 * Math.pow(2, this.timing.consecutiveFailures), 5e3) : 500;\n      await new Promise((resolve) => setTimeout(resolve, generationDelay));\n    }\n    this.continuousFetchLoopRunning = false;\n    if (this.debug) {\n      console.log(\n        `[CONTINUOUS-FETCH] URL generation loop ended (queued: ${this.adRequestQueue.length})`,\n        this.adRequestQueue.length > 0 ? { queuedUrls: [...this.adRequestQueue] } : {}\n      );\n    }\n  }\n  stopContinuousFetching() {\n    this.continuousFetchingActive = false;\n    this.continuousFetchLoopRunning = false;\n    this.placeholder.hide();\n    if (this.debug) {\n      console.log(\"[CONTINUOUS-FETCH] Stopping continuous ad fetching\");\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Ad iteration\n  // ───────────────────────────────────────────────────────────────\n  async tryNextAvailableAdWithRateLimit() {\n    if (!this.inAdBreak) {\n      return;\n    }\n    const epoch = this.timing.adBreakEpoch;\n    if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Too many consecutive failures (${this.timing.consecutiveFailures}), ending ad break gracefully`);\n      }\n      this.handleAdPodComplete();\n      return;\n    }\n    const backoffMultiplier = Math.pow(2, this.timing.consecutiveFailures);\n    const backoffDelay = Math.min(this.timing.backoffBaseMs * backoffMultiplier, this.timing.maxBackoffMs);\n    const effectiveMinInterval = this.timing.minAdRequestIntervalMs + (this.timing.consecutiveFailures > 0 ? backoffDelay : 0);\n    const timeSinceLastRequest = Date.now() - this.timing.lastAdRequestTime;\n    if (timeSinceLastRequest < effectiveMinInterval) {\n      const waitTime = effectiveMinInterval - timeSinceLastRequest;\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Rate limiting: waiting ${waitTime}ms before next request (backoff: ${this.timing.consecutiveFailures} failures)`);\n      }\n      await new Promise((resolve) => setTimeout(resolve, waitTime));\n    }\n    if (!this.inAdBreak || epoch !== this.timing.adBreakEpoch) {\n      return;\n    }\n    return this.tryNextAvailableAd(0);\n  }\n  async tryNextAvailableAd(retryCount = 0) {\n    if (!this.inAdBreak) {\n      return;\n    }\n    const remaining = this.timing.getRemainingAdMs();\n    if (!this.timing.hasTimeToStartAnotherAd()) {\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Not enough time remaining (${remaining}ms) to start another ad, ending ad break`);\n      }\n      this.handleAdPodComplete();\n      return;\n    }\n    if (this.timing.isGamInCooldown()) {\n      if (this.debug) {\n        console.log(\"[CIRCUIT-BREAKER] GAM in cooldown, ending ad break gracefully\");\n      }\n      this.handleAdPodComplete();\n      return;\n    }\n    if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Too many consecutive failures (${this.timing.consecutiveFailures}), ending ad break`);\n      }\n      this.handleAdPodComplete();\n      return;\n    }\n    this.timing.cleanupTemporaryFailures();\n    while (this.adRequestQueue.length > 0) {\n      const nextAdUrl = this.adRequestQueue.shift();\n      if (!nextAdUrl) continue;\n      if (this.timing.failedVastUrls.has(nextAdUrl)) {\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Skipping permanently-failed URL, trying next...\");\n        continue;\n      }\n      if (this.timing.isUrlInCooldown(nextAdUrl)) {\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Skipping URL in cooldown (recent no-fill), trying next...\");\n        continue;\n      }\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Requesting next ad via HLS ad player (${this.timing.currentAdIndex + 1}, ${this.adRequestQueue.length} remaining in queue)`);\n      }\n      try {\n        await this.playSingleAd(nextAdUrl);\n        this.timing.consecutiveFailures = 0;\n      } catch (error) {\n        const errorMessage = error.message;\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Ad request failed:\", errorMessage);\n        if (errorMessage.includes(\"ad_duration_exceeds_budget\")) {\n          await this.tryNextAvailableAdWithRateLimit();\n          return;\n        }\n        if (!errorMessage.includes(\"permanently failed\") && !errorMessage.includes(\"in cooldown\")) {\n          this.timing.consecutiveFailures++;\n        }\n        await this.tryNextAvailableAdWithRateLimit();\n      }\n      return;\n    }\n    const maxRetries = 3;\n    if (this.continuousFetchingActive && retryCount < maxRetries && remaining > 2e3) {\n      if (this.debug) {\n        console.log(`[CONTINUOUS-FETCH] Queue empty, waiting for URLs... (${retryCount + 1}/${maxRetries})`);\n      }\n      await new Promise((resolve) => setTimeout(resolve, 500));\n      await this.tryNextAvailableAd(retryCount + 1);\n      return;\n    }\n    if (!this.isShowingPlaceholder && remaining > 1e3) {\n      this.showPlaceholderAndWaitForAds();\n    } else {\n      if (this.debug) console.log(\"[CONTINUOUS-FETCH] No more ads available, ending ad break\");\n      this.handleAdPodComplete();\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Single ad playback\n  // ───────────────────────────────────────────────────────────────\n  async playSingleAd(vastTagUrl) {\n    const adPlayer = this.host.getAdPlayer();\n    if (adPlayer.isAdPlaying()) return;\n    if (this.timing.failedVastUrls.has(vastTagUrl)) {\n      if (this.debug) console.warn(\"[AD-ERROR] Skipping permanently-failed VAST URL:\", vastTagUrl);\n      throw new Error(\"VAST URL permanently failed\");\n    }\n    if (this.timing.isUrlInCooldown(vastTagUrl)) {\n      if (this.debug) console.warn(\"[AD-ERROR] Skipping URL in cooldown (recent no-fill):\", vastTagUrl);\n      throw new Error(\"VAST URL in cooldown after no-fill\");\n    }\n    if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n      if (this.debug) console.warn(\"[AD-ERROR] Too many consecutive failures, not requesting more ads\");\n      throw new Error(\"Too many consecutive failures\");\n    }\n    if (this.timing.isGamInCooldown()) {\n      if (this.debug) console.warn(\"[CIRCUIT-BREAKER] GAM in cooldown, skipping ad request\");\n      throw new Error(\"GAM in cooldown\");\n    }\n    this.recreateAdController();\n    const requestToken = ++this.timing.adRequestTokenCounter;\n    this.timing.activeAdRequestToken = requestToken;\n    this.timing.startAdRequestWatchdog(requestToken);\n    try {\n      await this.timing.enforceGlobalRateLimit();\n      this.timing.lastAdRequestTime = Date.now();\n      const ap = this.host.getAdPlayer();\n      await ap.requestAds(vastTagUrl);\n      sendAdLoadedTracking(\n        this.host.config.licenseKey,\n        { source: \"hls\", vastUrl: vastTagUrl, timestamp: (/* @__PURE__ */ new Date()).toISOString() },\n        this.analyticsContext\n      ).catch(() => {\n      });\n      this.timing.clearAdRequestWatchdog();\n      if (this.timing.activeAdRequestToken !== requestToken) return;\n      if (!this.timing.ensureLoadedAdFitsBudget(ap)) {\n        this.timing.rejectLoadedAdForDuration(ap);\n        this.recreateAdController();\n        throw new Error(\"ad_duration_exceeds_budget\");\n      }\n      try {\n        this.timing.startAdFailsafeTimer(requestToken);\n        await ap.play();\n        this.timing.markAdStarted();\n        if (this.timing.expectedAdBreakDurationMs != null && this.timing.getAdBreakEndWallClockMs() == null) {\n          this.timing.scheduleAdStopAtBreakBoundary();\n        }\n        ap.setAdVolume(getAdAudioVolume(ap));\n        this.timing.consecutiveFailures = 0;\n        this.timing.temporaryFailureUrls.delete(vastTagUrl);\n      } catch (playError) {\n        if (this.debug) console.error(\"[AD-ERROR] Failed to play ad:\", playError);\n        if (this.timing.isTemporaryAdError(playError)) {\n          this.timing.temporaryFailureUrls.set(vastTagUrl, Date.now());\n          if (this.debug) console.log(\"[AD-ERROR] Temporary play error - URL can be retried after cooldown\");\n        } else {\n          this.timing.failedVastUrls.add(vastTagUrl);\n          if (this.debug) console.log(\"[AD-ERROR] Permanent play error - URL blacklisted\");\n        }\n        this.timing.clearAdFailsafeTimer();\n        if (this.timing.activeAdRequestToken === requestToken) {\n          this.timing.activeAdRequestToken = null;\n        }\n        throw playError;\n      }\n    } catch (error) {\n      const errorMessage = error?.message || \"\";\n      if (this.debug) console.error(\"[AD-ERROR] Ad request failed:\", errorMessage);\n      if (this.timing.isTemporaryAdError(error)) {\n        this.timing.temporaryFailureUrls.set(vastTagUrl, Date.now());\n        if (this.debug) console.log(\"[AD-ERROR] Temporary error (no-fill/timeout) - URL can be retried after cooldown\");\n      } else {\n        this.timing.failedVastUrls.add(vastTagUrl);\n        if (this.debug) console.log(\"[AD-ERROR] Permanent error - URL blacklisted:\", errorMessage);\n      }\n      this.timing.clearAdRequestWatchdog();\n      this.timing.clearAdFailsafeTimer();\n      if (this.timing.activeAdRequestToken === requestToken) {\n        this.timing.activeAdRequestToken = null;\n      }\n      throw error;\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Placeholder wait\n  // ───────────────────────────────────────────────────────────────\n  async showPlaceholderAndWaitForAds() {\n    const remaining = this.timing.getRemainingAdMs();\n    const waitTime = Math.min(this.maxPlaceholderDurationMs, remaining);\n    if (this.timing.isGamInCooldown()) {\n      if (this.debug) console.log(\"[CIRCUIT-BREAKER] GAM in cooldown, skipping placeholder wait\");\n      this.handleAdPodComplete();\n      return;\n    }\n    if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n      if (this.debug) console.log(\"[CONTINUOUS-FETCH] Skipping placeholder - too many consecutive failures\");\n      this.handleAdPodComplete();\n      return;\n    }\n    if (waitTime < 1e3) {\n      this.handleAdPodComplete();\n      return;\n    }\n    if (this.debug) {\n      console.log(`[CONTINUOUS-FETCH] Showing placeholder for ${waitTime}ms while waiting for ad URLs`);\n    }\n    this.isShowingPlaceholder = true;\n    this.host.getAdPlayer().showPlaceholder();\n    const checkInterval = 300;\n    const maxChecks = Math.floor(waitTime / checkInterval);\n    for (let i = 0; i < maxChecks; i++) {\n      await new Promise((resolve) => setTimeout(resolve, checkInterval));\n      if (!this.inAdBreak) return;\n      if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Too many failures during placeholder wait\");\n        break;\n      }\n      if (!this.timing.hasTimeToStartAnotherAd()) {\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Not enough time remaining during placeholder wait, ending ad break\");\n        break;\n      }\n      while (this.adRequestQueue.length > 0) {\n        if (!this.timing.hasTimeToStartAnotherAd()) break;\n        const nextAdUrl = this.adRequestQueue.shift();\n        if (!nextAdUrl) continue;\n        if (this.timing.failedVastUrls.has(nextAdUrl)) continue;\n        if (this.timing.isUrlInCooldown(nextAdUrl)) continue;\n        if (this.debug) console.log(\"[CONTINUOUS-FETCH] Ad URL available, requesting via HLS ad player\");\n        this.isShowingPlaceholder = false;\n        this.host.getAdPlayer().hidePlaceholder();\n        try {\n          await this.playSingleAd(nextAdUrl);\n          this.timing.consecutiveFailures = 0;\n        } catch (error) {\n          const errorMessage = error.message;\n          if (errorMessage.includes(\"ad_duration_exceeds_budget\")) {\n            await this.tryNextAvailableAdWithRateLimit();\n            return;\n          }\n          if (!errorMessage.includes(\"permanently failed\") && !errorMessage.includes(\"in cooldown\")) {\n            this.timing.consecutiveFailures++;\n          }\n          await this.tryNextAvailableAdWithRateLimit();\n        }\n        return;\n      }\n    }\n    if (this.debug) console.log(\"[CONTINUOUS-FETCH] Placeholder timeout, ending ad break\");\n    this.isShowingPlaceholder = false;\n    this.host.getAdPlayer().hidePlaceholder();\n    this.handleAdPodComplete();\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Ad break completion\n  // ───────────────────────────────────────────────────────────────\n  handleAdPodComplete() {\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Ad pod complete - cleaning up\");\n    }\n    this.timing.resetForBreakEnd();\n    this.stopContinuousFetching();\n    this.clearPendingAdBreak();\n    if (this.isShowingPlaceholder) {\n      this.host.getAdPlayer().hidePlaceholder();\n      this.isShowingPlaceholder = false;\n    }\n    this.adRequestQueue = [];\n    this.inAdBreak = false;\n    this.adDetectSentForCurrentBreak = false;\n    this.cueManager.activeScte35BreakKey = void 0;\n    this.cueManager.scheduledScte35BreakKey = void 0;\n    this.adPodQueue = [];\n    this.showAds = false;\n    this.host.getAdPlayer().stop().catch(() => {\n    });\n    const restoredMuted = this.host.getAdPlayer().getOriginalMutedState();\n    const restoredVolume = this.host.getAdPlayer().getOriginalVolume();\n    if (this.host.video.muted !== restoredMuted) {\n      this.host.video.muted = restoredMuted;\n    }\n    if (Math.abs(this.host.video.volume - restoredVolume) > 0.01) {\n      this.host.video.volume = restoredVolume;\n    }\n    this.host.video.style.visibility = \"visible\";\n    this.host.video.style.opacity = \"1\";\n    if (this.host.isLiveStream()) {\n      const liveSyncPos = this.host.getLiveSyncPosition();\n      if (liveSyncPos != null && liveSyncPos > this.host.video.currentTime) {\n        if (this.debug) {\n          console.log(\n            `[StormcloudVideoPlayer] Live break end \\u2014 snapping to live edge: ${this.host.video.currentTime.toFixed(2)}s \\u2192 ${liveSyncPos.toFixed(2)}s`\n          );\n        }\n        this.host.video.currentTime = liveSyncPos;\n        this.host.restartHlsLoad(liveSyncPos);\n      }\n      this.resumeContentPlayback();\n      this.monitorLiveResumeStall(this.host.video.currentTime);\n      return;\n    }\n    this.resumeContentPlayback();\n  }\n  getBufferedAhead() {\n    const video = this.host.video;\n    const t = video.currentTime;\n    const ranges = video.buffered;\n    for (let i = 0; i < ranges.length; i++) {\n      if (t >= ranges.start(i) - 0.5 && t <= ranges.end(i)) {\n        return ranges.end(i) - t;\n      }\n    }\n    return 0;\n  }\n  describeVideoState() {\n    const v = this.host.video;\n    const networkStates = [\"EMPTY\", \"IDLE\", \"LOADING\", \"NO_SOURCE\"];\n    const readyStates = [\n      \"HAVE_NOTHING\",\n      \"HAVE_METADATA\",\n      \"HAVE_CURRENT_DATA\",\n      \"HAVE_FUTURE_DATA\",\n      \"HAVE_ENOUGH_DATA\"\n    ];\n    const net = networkStates[v.networkState] ?? String(v.networkState);\n    const ready = readyStates[v.readyState] ?? String(v.readyState);\n    const err = v.error ? `code=${v.error.code}${v.error.message ? ` (${v.error.message})` : \"\"}` : \"none\";\n    const ranges = [];\n    for (let i = 0; i < v.buffered.length; i++) {\n      ranges.push(`[${v.buffered.start(i).toFixed(2)}\\u2013${v.buffered.end(i).toFixed(2)}]`);\n    }\n    return `t=${v.currentTime.toFixed(2)}s paused=${v.paused} ended=${v.ended} seeking=${v.seeking} readyState=${ready} networkState=${net} error=${err} buffered=${ranges.length ? ranges.join(\",\") : \"none\"}`;\n  }\n  monitorLiveResumeStall(resumeBaseline) {\n    const pollIntervalMs = 1e3;\n    const graceMs = 5e3;\n    const recoveryCooldownMs = 5e3;\n    const maxRecoveries = 3;\n    const maxMonitorMs = 45e3;\n    const startTime = Date.now();\n    let baseline = resumeBaseline;\n    let recoveries = 0;\n    let lastRecoveryAt = 0;\n    const video = this.host.video;\n    let listenersAttached = false;\n    let onMediaEvent;\n    const diagEvents = [\n      \"loadstart\",\n      \"loadedmetadata\",\n      \"loadeddata\",\n      \"canplay\",\n      \"canplaythrough\",\n      \"play\",\n      \"playing\",\n      \"pause\",\n      \"waiting\",\n      \"stalled\",\n      \"suspend\",\n      \"seeking\",\n      \"seeked\",\n      \"emptied\",\n      \"error\",\n      \"ended\"\n    ];\n    if (this.debug) {\n      onMediaEvent = (e) => {\n        const dt = ((Date.now() - startTime) / 1e3).toFixed(1);\n        console.log(\n          `[ResumeDiag] +${dt}s event=${e.type} \\u2014 ${this.describeVideoState()}`\n        );\n      };\n      for (const name of diagEvents) {\n        video.addEventListener(name, onMediaEvent);\n      }\n      listenersAttached = true;\n      console.log(\n        `[ResumeDiag] +0.0s monitor start \\u2014 ${this.describeVideoState()}`\n      );\n    }\n    const cleanup = () => {\n      if (listenersAttached && onMediaEvent) {\n        for (const name of diagEvents) {\n          video.removeEventListener(name, onMediaEvent);\n        }\n        listenersAttached = false;\n      }\n    };\n    const poll = () => {\n      if (this.inAdBreak) {\n        cleanup();\n        return;\n      }\n      const currentTime = video.currentTime;\n      const advanced = currentTime > baseline + 0.5;\n      const playing = !video.paused && video.readyState >= 3;\n      if (advanced && playing) {\n        if (this.debug) {\n          console.log(\n            `[StormcloudVideoPlayer] Live stream resumed successfully after ad break \\u2014 ${this.describeVideoState()}`\n          );\n        }\n        cleanup();\n        return;\n      }\n      if (video.paused) {\n        video.play()?.catch(() => {\n        });\n      }\n      const elapsed = Date.now() - startTime;\n      const bufferedAhead = this.getBufferedAhead();\n      const wedged = bufferedAhead < 0.5 && !advanced;\n      if (elapsed >= maxMonitorMs) {\n        if (this.debug && !advanced) {\n          console.warn(\n            `[StormcloudVideoPlayer] Live stream failed to resume after ${(maxMonitorMs / 1e3).toFixed(0)}s \\u2014 ${this.describeVideoState()}`\n          );\n        }\n        cleanup();\n        return;\n      }\n      const canRecover = wedged && elapsed >= graceMs && Date.now() - lastRecoveryAt >= recoveryCooldownMs && recoveries < maxRecoveries;\n      if (canRecover) {\n        recoveries++;\n        lastRecoveryAt = Date.now();\n        if (recoveries === 1) {\n          if (this.debug) {\n            console.warn(\n              `[StormcloudVideoPlayer] Content wedged after ad break \\u2014 calling recoverMediaError() (recovery ${recoveries}/${maxRecoveries}) \\u2014 ${this.describeVideoState()}`\n            );\n          }\n          this.host.recoverMediaError();\n        } else if (recoveries === 2) {\n          const liveSyncPos = this.host.getLiveSyncPosition();\n          const reloadPos = liveSyncPos != null && liveSyncPos > currentTime ? liveSyncPos : currentTime;\n          if (this.debug) {\n            console.warn(\n              `[StormcloudVideoPlayer] Content wedged after ad break \\u2014 restarting HLS load at ${reloadPos.toFixed(2)}s (recovery ${recoveries}/${maxRecoveries}) \\u2014 ${this.describeVideoState()}`\n            );\n          }\n          if (liveSyncPos != null && liveSyncPos > currentTime) {\n            video.currentTime = liveSyncPos;\n          }\n          this.host.restartHlsLoad(reloadPos);\n        } else {\n          if (this.debug) {\n            console.warn(\n              `[StormcloudVideoPlayer] Content still wedged after ad break \\u2014 hard-reloading live stream (recovery ${recoveries}/${maxRecoveries}) \\u2014 ${this.describeVideoState()}`\n            );\n          }\n          this.host.reloadLiveStream();\n        }\n        baseline = video.currentTime;\n        if (video.paused) {\n          video.play()?.catch(() => {\n          });\n        }\n      }\n      window.setTimeout(poll, pollIntervalMs);\n    };\n    window.setTimeout(poll, pollIntervalMs);\n  }\n  resumeContentPlayback(attempt = 0) {\n    const maxAttempts = 5;\n    const video = this.host.video;\n    if (!video.paused) {\n      if (this.debug && attempt === 0) {\n        console.log(\"[StormcloudVideoPlayer] Content video already playing after ads\");\n      }\n      return;\n    }\n    if (this.debug) {\n      console.log(\n        `[StormcloudVideoPlayer] Resuming content playback after ads (attempt ${attempt + 1}/${maxAttempts}, readyState=${video.readyState})`\n      );\n    }\n    if (video.readyState < 3) {\n      if (attempt + 1 >= maxAttempts) {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] readyState never reached HAVE_FUTURE_DATA, forcing play()\"\n          );\n        }\n        video.play()?.catch(() => {\n        });\n        return;\n      }\n      const onReady = () => {\n        video.removeEventListener(\"canplay\", onReady);\n        this.resumeContentPlayback(attempt + 1);\n      };\n      video.addEventListener(\"canplay\", onReady);\n      const backoffMs = 500 * (attempt + 1);\n      window.setTimeout(() => {\n        video.removeEventListener(\"canplay\", onReady);\n        if (video.paused) {\n          this.resumeContentPlayback(attempt + 1);\n        }\n      }, backoffMs);\n      return;\n    }\n    const playResult = video.play();\n    if (playResult && typeof playResult.catch === \"function\") {\n      playResult.catch((error) => {\n        if (attempt + 1 >= maxAttempts) {\n          if (this.debug) {\n            console.warn(\n              \"[StormcloudVideoPlayer] Failed to resume content playback after ads:\",\n              error\n            );\n          }\n          return;\n        }\n        const backoffMs = 250 * (attempt + 1);\n        window.setTimeout(() => {\n          this.resumeContentPlayback(attempt + 1);\n        }, backoffMs);\n      });\n    }\n  }\n  handleAdFailure() {\n    this.timing.consecutiveFailures++;\n    this.timing.recordGamNoFill();\n    const remaining = this.timing.getRemainingAdMs();\n    if (this.debug) {\n      console.log(\n        `[CONTINUOUS-FETCH] Ad failure: remaining=${remaining}ms, queued ads=${this.adRequestQueue.length}, consecutiveFailures=${this.timing.consecutiveFailures}`,\n        this.adRequestQueue.length > 0 ? { queuedUrls: [...this.adRequestQueue] } : {}\n      );\n    }\n    if (this.timing.consecutiveFailures >= this.timing.maxConsecutiveFailures) {\n      if (this.debug) console.log(`[CONTINUOUS-FETCH] Max consecutive failures reached (${this.timing.consecutiveFailures}), ending ad break gracefully`);\n      this.handleAdPodComplete();\n      return;\n    }\n    if (this.timing.hasTimeToStartAnotherAd()) {\n      this.tryNextAvailableAdWithRateLimit();\n    } else {\n      if (this.debug) console.log(\"[AD-ERROR] Ad failed and not enough time remaining for another ad. Failed URLs:\", this.timing.failedVastUrls.size);\n      this.handleAdPodComplete();\n    }\n  }\n};\n\n// src/player/StormcloudVideoPlayer.ts\nvar StormcloudVideoPlayer = class {\n  constructor(config) {\n    this.attached = false;\n    this.palPlaybackStarted = false;\n    initializePolyfills();\n    const browserOverrides = getBrowserConfigOverrides();\n    this.config = { ...browserOverrides, ...config };\n    this.video = config.videoElement;\n    logBrowserInfo(config.debugAdTiming);\n    this.adPlayer = this.createAdPlayer(false);\n    this.palNonce = createPalNonceManager();\n    this.cueManager = new Scte35CueManager(!!this.config.debugAdTiming, {\n      onEarlyStartCue: (marker, fragmentSn, cueKey) => {\n        this.startAdPrefetch(marker, fragmentSn, cueKey);\n      },\n      onPlaybackCue: (marker, cueKey) => {\n        this.onScte35Marker(marker, cueKey);\n      },\n      isInAdBreak: () => this.adBreak.inAdBreak\n    });\n    this.adConfig = new AdConfigManager(this.config, this.video);\n    this.timing = new AdTimingService(this.config, this.video, {\n      onAdStopTimerFired: () => this.onAdStopTimerFired(),\n      onAdStartTimerFired: (marker, cueKey) => {\n        this.startScte35AdBreak(\n          marker,\n          cueKey,\n          marker.durationSeconds != null ? marker.durationSeconds * 1e3 : this.timing.expectedAdBreakDurationMs\n        );\n      },\n      onWatchdogTimeout: () => this.adBreak.handleAdFailure(),\n      onFailsafeTimeout: () => this.adBreak.handleAdFailure()\n    });\n    this.placeholder = new PlaceholderLayer(this.video, !!this.config.debugAdTiming);\n    this.hlsEngine = new HlsEngine(this.config, this.video, this.cueManager, this.timing, {\n      onManifestParsed: async (isLive) => this.onManifestParsed(isLive),\n      onScte35Cue: (marker, context) => this.cueManager.onScte35Cue(marker, context),\n      activatePendingCuesForFragment: (frag) => this.cueManager.activatePendingScte35CuesForFragment(frag),\n      onFatalDestroy: () => this.destroy(),\n      isInAdBreak: () => this.adBreak.inAdBreak,\n      hasPendingAdBreak: () => this.adBreak.pendingAdBreak !== null\n    });\n    this.adBreak = new AdBreakOrchestrator(\n      {\n        config: this.config,\n        video: this.video,\n        getAdPlayer: () => this.adPlayer,\n        setAdPlayer: (p) => {\n          this.adPlayer = p;\n        },\n        createAdPlayer: (c) => this.createAdPlayer(c),\n        shouldContinueLiveStreamDuringAds: () => this.shouldContinueLiveStreamDuringAds(),\n        isLiveStream: () => this.hlsEngine.isLiveStream,\n        getLiveSyncPosition: () => this.hlsEngine.getLiveSyncPosition(),\n        restartHlsLoad: (position) => this.hlsEngine.restartLoadAt(position),\n        reloadLiveStream: () => this.hlsEngine.reloadLiveStream(),\n        recoverMediaError: () => this.hlsEngine.recoverMediaError(),\n        generatePodVastUrl: (base, breakDurationMs) => this.generatePodVastUrl(base, breakDurationMs)\n      },\n      this.timing,\n      this.adConfig,\n      this.cueManager,\n      this.placeholder\n    );\n  }\n  get debug() {\n    return !!this.config.debugAdTiming;\n  }\n  createAdPlayer(continueLiveStreamDuringAds) {\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Creating HLS ad player\");\n    }\n    return createHlsAdPlayer(this.video, {\n      continueLiveStreamDuringAds,\n      ...this.config.licenseKey ? { licenseKey: this.config.licenseKey } : {},\n      ...this.hlsEngine?.hls ? { mainHlsInstance: this.hlsEngine.hls } : {}\n    });\n  }\n  generatePodVastUrl(baseUrl, breakDurationMs) {\n    const podParams = this.adConfig.resolvePodParams(breakDurationMs);\n    return this.adConfig.generatePodVastUrl(\n      baseUrl,\n      podParams,\n      this.adPlayer,\n      this.palNonce,\n      this.adBreak.inAdBreak\n    );\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Lifecycle\n  // ───────────────────────────────────────────────────────────────\n  async load() {\n    if (!this.attached) {\n      this.attach();\n    }\n    try {\n      await this.adConfig.fetchAdConfiguration();\n    } catch (error) {\n      if (this.debug) {\n        console.warn(\n          \"[StormcloudVideoPlayer] Failed to fetch ad configuration:\",\n          error\n        );\n      }\n    }\n    this.palNonce.generateNonce({\n      videoWidth: this.video.offsetWidth || this.video.clientWidth || 640,\n      videoHeight: this.video.offsetHeight || this.video.clientHeight || 480,\n      adWillAutoPlay: !!this.config.autoplay,\n      adWillPlayMuted: true,\n      playerVolume: 0,\n      continuousPlayback: this.config.lowLatencyMode ?? false\n    }).catch(() => {\n    });\n    fetchConsentSignals().then((signals) => {\n      this.adConfig.consentSignals = signals;\n    }).catch(() => {\n    });\n    this.adConfig.initializeTracking();\n    if (this.hlsEngine.shouldUseNativeHls(() => this.getStreamType())) {\n      await this.hlsEngine.setupNativeHls();\n      const continueLiveStreamDuringAds = this.shouldContinueLiveStreamDuringAds();\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Native HLS ad behavior:\", {\n          isLive: this.hlsEngine.isLiveStream,\n          continueLiveStreamDuringAds\n        });\n      }\n      this.adPlayer.destroy();\n      this.adPlayer = this.createAdPlayer(continueLiveStreamDuringAds);\n      this.adPlayer.initialize();\n      return;\n    }\n    this.hlsEngine.setupHls();\n  }\n  async onManifestParsed(isLive) {\n    if (this.hlsEngine.reloadingLiveStream) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Manifest re-parsed after hard reload \\u2014 skipping ad-player setup\");\n      }\n      return;\n    }\n    if (!this.adConfig.isVmapEnabled() && !isLive && this.adConfig.vmapBreaks.length === 0 && this.adConfig.apiVastTagUrl) {\n      const prerollKey = \"synthetic-vod-preroll\";\n      if (!this.adConfig.consumedVmapBreakIds.has(prerollKey)) {\n        this.adConfig.vmapBreaks = [\n          { id: prerollKey, startTimeMs: 0, vastTagUrl: this.adConfig.apiVastTagUrl }\n        ];\n        if (this.debug) {\n          console.log(\n            \"[StormcloudVideoPlayer] Injected synthetic VOD preroll from apiVastTagUrl\"\n          );\n        }\n      }\n    }\n    if (this.debug) {\n      const adBehavior = this.shouldContinueLiveStreamDuringAds() ? \"live (main video continues muted during ads)\" : \"vod (main video pauses during ads)\";\n      console.log(\"[StormcloudVideoPlayer] Stream type detected:\", {\n        isLive,\n        allowNativeHls: this.config.allowNativeHls,\n        adBehavior\n      });\n    }\n    this.adPlayer.destroy();\n    this.adPlayer = this.createAdPlayer(this.shouldContinueLiveStreamDuringAds());\n    this.adPlayer.initialize();\n  }\n  attach() {\n    if (this.attached) return;\n    this.attached = true;\n    this.video.autoplay = !!this.config.autoplay;\n    this.video.muted = !!this.config.muted;\n    this.adPlayer.initialize();\n    this.adPlayer.updateOriginalMutedState(this.video.muted, this.video.volume);\n    this.adBreak.attachImaEventListeners();\n    this.video.addEventListener(\"play\", () => {\n      if (!this.palPlaybackStarted && !this.adPlayer.isAdPlaying()) {\n        this.palPlaybackStarted = true;\n        this.palNonce.sendPlaybackStart();\n      }\n    });\n    this.endedHandler = () => {\n      if (this.palPlaybackStarted) {\n        this.palPlaybackStarted = false;\n        this.palNonce.sendPlaybackEnd();\n      }\n      this.onVideoEnded();\n    };\n    this.video.addEventListener(\"ended\", this.endedHandler);\n    this.video.addEventListener(\"mousedown\", (e) => {\n      this.palNonce.sendAdTouch(e);\n    });\n    this.video.addEventListener(\"touchstart\", (e) => {\n      this.palNonce.sendAdTouch(e);\n    });\n    this.timeUpdateHandler = () => {\n      this.onTimeUpdate(this.video.currentTime);\n    };\n    this.video.addEventListener(\"timeupdate\", this.timeUpdateHandler);\n    this.emptiedHandler = () => {\n      if (this.hlsEngine.nativeHlsMode && this.hlsEngine.videoSrcProtection && !this.adPlayer.isAdPlaying()) {\n        if (this.debug) {\n          console.log(\n            \"[StormcloudVideoPlayer] Video src was cleared, restoring:\",\n            this.hlsEngine.videoSrcProtection\n          );\n        }\n        const currentTime = this.video.currentTime;\n        const wasPaused = this.video.paused;\n        this.video.src = this.hlsEngine.videoSrcProtection;\n        this.video.currentTime = currentTime;\n        if (!wasPaused) {\n          this.video.play().catch(() => {\n          });\n        }\n      }\n    };\n    this.video.addEventListener(\"emptied\", this.emptiedHandler);\n  }\n  shouldContinueLiveStreamDuringAds() {\n    if (this.config.pauseContentDuringAds) {\n      return false;\n    }\n    if (this.hlsEngine.isLiveStream) {\n      return true;\n    }\n    const duration = this.video.duration;\n    if (!Number.isFinite(duration) || duration === Infinity) {\n      return true;\n    }\n    return false;\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  SCTE-35 marker orchestration\n  // ───────────────────────────────────────────────────────────────\n  onScte35Marker(marker, cueKey) {\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] SCTE-35 marker detected:\", {\n        type: marker.type,\n        ptsSeconds: marker.ptsSeconds,\n        durationSeconds: marker.durationSeconds,\n        currentTime: this.video.currentTime,\n        raw: marker.raw,\n        hasPendingAdBreak: !!this.adBreak.pendingAdBreak\n      });\n    }\n    if (marker.type === \"start\") {\n      if (this.adBreak.inAdBreak) {\n        if (marker.durationSeconds != null) {\n          const newDurationMs = marker.durationSeconds * 1e3;\n          if (this.timing.expectedAdBreakDurationMs == null || newDurationMs > this.timing.expectedAdBreakDurationMs) {\n            this.timing.setAdBreakDurationBoundary(newDurationMs);\n            this.timing.scheduleAdStopAtBreakBoundary();\n            if (this.debug) {\n              console.log(\n                `[StormcloudVideoPlayer] Updated ad break duration from subsequent marker: ${newDurationMs}ms, remaining: ${this.timing.getWallClockRemainingAdMs()}ms`\n              );\n            }\n          }\n        }\n        return;\n      }\n      if (!this.adBreak.adDetectSentForCurrentBreak) {\n        this.adBreak.adDetectSentForCurrentBreak = true;\n        const detectPayload = {};\n        if (marker.durationSeconds != null) detectPayload.durationSeconds = marker.durationSeconds;\n        if (marker.ptsSeconds != null) detectPayload.ptsSeconds = marker.ptsSeconds;\n        sendAdDetectTracking(this.config.licenseKey, { source: \"scte35\", timestamp: (/* @__PURE__ */ new Date()).toISOString(), ...detectPayload }, buildAnalyticsContext(this.config)).catch(() => {\n        });\n      }\n      const hasPrefetchedAds = this.adBreak.pendingAdBreak && this.adBreak.pendingAdBreak.vastUrls.length > 0;\n      const durationMs = marker.durationSeconds != null ? marker.durationSeconds * 1e3 : this.adBreak.pendingAdBreak?.marker.durationSeconds != null ? this.adBreak.pendingAdBreak.marker.durationSeconds * 1e3 : void 0;\n      const isManifest = isManifestBasedMarker(marker);\n      const forceImmediate = this.config.immediateManifestAds ?? true;\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Ad start decision:\", {\n          isManifestMarker: isManifest,\n          forceImmediate,\n          hasPts: typeof marker.ptsSeconds === \"number\",\n          hasPrefetchedAds\n        });\n      }\n      if (isManifest && forceImmediate) {\n        if (this.debug) {\n          console.log(\n            `[StormcloudVideoPlayer] Starting ad immediately (manifest-based)${hasPrefetchedAds ? \" with prefetched ads\" : \"\"}`\n          );\n        }\n        this.timing.clearAdStartTimer();\n        this.startScte35AdBreak(marker, cueKey, durationMs);\n      } else if (typeof marker.ptsSeconds === \"number\") {\n        const tol = this.config.driftToleranceMs ?? 1e3;\n        const nowMs = this.video.currentTime * 1e3;\n        const estCurrentPtsMs = nowMs - this.timing.ptsDriftEmaMs;\n        const deltaMs = Math.floor(marker.ptsSeconds * 1e3 - estCurrentPtsMs);\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] PTS-based timing calculation:\", {\n            nowMs,\n            estCurrentPtsMs,\n            markerPtsMs: marker.ptsSeconds * 1e3,\n            deltaMs,\n            tolerance: tol\n          });\n        }\n        if (deltaMs > tol) {\n          if (this.debug) {\n            console.log(`[StormcloudVideoPlayer] Scheduling ad start in ${deltaMs}ms`);\n          }\n          this.timing.expectedAdBreakDurationMs = durationMs;\n          this.cueManager.scheduledScte35BreakKey = cueKey;\n          this.timing.scheduleAdStartIn(deltaMs, marker, cueKey);\n        } else {\n          if (this.debug) {\n            console.log(\"[StormcloudVideoPlayer] Starting ad immediately (within tolerance)\");\n          }\n          this.timing.clearAdStartTimer();\n          this.startScte35AdBreak(marker, cueKey, durationMs);\n        }\n      } else {\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] Starting ad immediately (fallback)\");\n        }\n        this.timing.clearAdStartTimer();\n        this.startScte35AdBreak(marker, cueKey, durationMs);\n      }\n      return;\n    }\n    if (marker.type === \"progress\" && this.adBreak.inAdBreak) {\n      if (marker.durationSeconds != null) {\n        this.timing.setAdBreakDurationBoundary(marker.durationSeconds * 1e3);\n      }\n      this.timing.scheduleAdStopAtBreakBoundary();\n      if (!this.adPlayer.isAdPlaying() && this.timing.activeAdRequestToken === null && this.adBreak.adRequestQueue.length > 0 && this.timing.hasTimeToStartAnotherAd()) {\n        this.adBreak.tryNextAvailableAdWithRateLimit();\n      }\n      return;\n    }\n    if (marker.type === \"end\") {\n      if (!this.video.muted) {\n        this.video.muted = true;\n        if (this.debug) {\n          console.log(\"[StormcloudVideoPlayer] Muted video on SCTE end marker\");\n        }\n      }\n      const remaining = this.timing.getRemainingAdMs();\n      const adPlaying = this.adPlayer.isAdPlaying();\n      const hasQueuedAds = this.adBreak.adRequestQueue.length > 0;\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] SCTE-35 end marker received:\", {\n          remaining,\n          adPlaying,\n          hasQueuedAds,\n          activeAdRequest: this.timing.activeAdRequestToken !== null\n        });\n      }\n      this.timing.scteAdBreakEndWallClockMs = Date.now();\n      this.timing.clearAdStartTimer();\n      this.timing.clearAdStopTimer();\n      if (adPlaying) {\n        this.adPlayer.stop().catch(() => {\n        });\n      }\n      this.adBreak.handleAdPodComplete();\n      return;\n    }\n  }\n  startScte35AdBreak(marker, cueKey, durationMs) {\n    this.adBreak.inAdBreak = true;\n    this.cueManager.activeScte35BreakKey = cueKey ?? this.cueManager.pendingScte35CueKey;\n    this.cueManager.scheduledScte35BreakKey = void 0;\n    this.timing.currentAdBreakStartWallClockMs = this.timing.resolveScteBreakStartWallClockMs(marker);\n    this.timing.setAdBreakDurationBoundary(durationMs);\n    this.adBreak.handleAdStart(marker);\n    this.timing.scheduleAdStopAtBreakBoundary();\n  }\n  onAdStopTimerFired() {\n    if (!this.adBreak.inAdBreak) return;\n    const adPlaying = this.adPlayer.isAdPlaying();\n    const checkIntervalMs = Math.max(\n      250,\n      Math.floor(this.config.adBreakCheckIntervalMs ?? 1e3)\n    );\n    const maxExtensionMsConfig = this.config.maxAdBreakExtensionMs;\n    const maxExtensionMs = typeof maxExtensionMsConfig === \"number\" && maxExtensionMsConfig > 0 ? maxExtensionMsConfig : 0;\n    const endWallClockMs = this.timing.getAdBreakEndWallClockMs() ?? Date.now();\n    const overrunMs = Math.max(0, Date.now() - endWallClockMs);\n    const shouldExtendAdBreak = adPlaying && overrunMs < maxExtensionMs;\n    if (shouldExtendAdBreak) {\n      this.timing.scheduleAdStopCountdown(checkIntervalMs);\n      return;\n    }\n    if (this.debug) {\n      console.log(\n        `[StormcloudVideoPlayer] Ad break boundary reached (overrun=${overrunMs}ms) - hard-stopping ads and resuming stream`\n      );\n    }\n    if (adPlaying) {\n      this.adPlayer.stop().catch(() => {\n      });\n    }\n    this.adBreak.handleAdPodComplete();\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Ad prefetch\n  // ───────────────────────────────────────────────────────────────\n  startAdPrefetch(marker, fragmentSn, cueKey) {\n    if (this.adBreak.pendingAdBreak || this.adBreak.inAdBreak) return;\n    const scheduled = this.adConfig.findCurrentOrNextBreak(this.video.currentTime * 1e3);\n    const tags = this.adConfig.selectVastTagsForBreak(scheduled);\n    let baseVastUrl;\n    if (tags && tags.length > 0 && tags[0]) {\n      baseVastUrl = tags[0];\n    } else if (this.adConfig.apiVastTagUrl) {\n      baseVastUrl = this.adConfig.apiVastTagUrl;\n    } else {\n      if (this.debug) console.warn(\"[StormcloudVideoPlayer] No VAST URL available for prefetch\");\n      return;\n    }\n    this.adConfig.beginNewAdPod();\n    this.adConfig.podAssignedByPrefetch = true;\n    const breakDurationMs = marker.durationSeconds != null ? marker.durationSeconds * 1e3 : void 0;\n    const generatedUrls = [this.generatePodVastUrl(baseVastUrl, breakDurationMs)];\n    this.adBreak.pendingAdBreak = {\n      marker,\n      ...fragmentSn !== void 0 ? { detectedAtFragmentSn: fragmentSn } : {},\n      vastUrls: generatedUrls,\n      isFetching: false,\n      fetchStartTime: Date.now()\n    };\n    this.cueManager.pendingScte35CueKey = cueKey;\n    this.adBreak.adDetectSentForCurrentBreak = true;\n    const detectPayload = {};\n    if (marker.durationSeconds != null) detectPayload.durationSeconds = marker.durationSeconds;\n    if (marker.ptsSeconds != null) detectPayload.ptsSeconds = marker.ptsSeconds;\n    if (fragmentSn !== void 0) detectPayload.detectedAtFragmentSn = fragmentSn;\n    sendAdDetectTracking(this.config.licenseKey, { source: \"scte35\", timestamp: (/* @__PURE__ */ new Date()).toISOString(), ...detectPayload }, buildAnalyticsContext(this.config)).catch(() => {\n    });\n    if (this.debug) {\n      console.log(\"[PREFETCH] Starting ad prefetch for upcoming ad break\");\n      console.log(`[PREFETCH] Pre-generated pod request URL`);\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  VMAP time-based ad breaks\n  // ───────────────────────────────────────────────────────────────\n  onTimeUpdate(currentTimeSec) {\n    if (!this.adConfig.isVmapEnabled() || this.adConfig.vmapBreaks.length === 0) return;\n    if (this.adPlayer.isAdPlaying() || this.adBreak.inAdBreak) return;\n    const nowMs = currentTimeSec * 1e3;\n    const breakToPlay = this.adConfig.findBreakForTime(nowMs);\n    if (breakToPlay) {\n      void this.handleVmapAdBreak(breakToPlay, nowMs).catch((error) => {\n        if (this.debug) {\n          console.warn(\"[StormcloudVideoPlayer] VMAP ad break failed gracefully:\", error);\n        }\n      });\n    }\n  }\n  onVideoEnded() {\n    if (!this.adConfig.isVmapEnabled() || this.adConfig.vmapBreaks.length === 0) return;\n    if (this.adPlayer.isAdPlaying() || this.adBreak.inAdBreak) return;\n    const durationMs = Number.isFinite(this.video.duration) ? Math.floor(this.video.duration * 1e3) : 0;\n    const postroll = this.adConfig.vmapBreaks.find(\n      (b) => b.startTimeMs === -1 && !this.adConfig.consumedVmapBreakIds.has(this.adConfig.getAdBreakKey(b))\n    );\n    if (postroll) {\n      void this.handleVmapAdBreak(postroll, durationMs).catch((error) => {\n        if (this.debug) {\n          console.warn(\"[StormcloudVideoPlayer] VMAP post-roll failed gracefully:\", error);\n        }\n      });\n    }\n  }\n  async handleVmapAdBreak(adBreak, nowMs) {\n    const key = this.adConfig.getAdBreakKey(adBreak);\n    if (this.adConfig.consumedVmapBreakIds.has(key)) return;\n    const breakStartMs = this.adConfig.resolveBreakStartMs(adBreak);\n    if (breakStartMs == null) return;\n    const durationMs = adBreak.durationMs ?? 0;\n    const endMs = breakStartMs + durationMs;\n    const inWindow = durationMs > 0 ? nowMs >= breakStartMs && nowMs < endMs : nowMs >= breakStartMs;\n    if (inWindow) {\n      this.adConfig.consumedVmapBreakIds.add(key);\n      const tags = this.adConfig.selectVastTagsForBreak(adBreak);\n      if (!tags || tags.length === 0) return;\n      const first = tags[0];\n      const rest = tags.slice(1);\n      this.adBreak.adPodQueue = rest;\n      this.adPlayer.updateOriginalMutedState(this.video.muted, this.video.volume);\n      this.adBreak.showAds = true;\n      this.adBreak.inAdBreak = true;\n      this.timing.currentAdBreakStartWallClockMs = Date.now();\n      try {\n        await this.adBreak.playSingleAd(first);\n      } catch (error) {\n        if (this.debug) {\n          console.warn(\"[StormcloudVideoPlayer] VMAP ad request failed:\", error);\n        }\n        this.adBreak.handleAdPodComplete();\n      }\n    }\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Public API\n  // ───────────────────────────────────────────────────────────────\n  getCurrentAdIndex() {\n    return this.timing.currentAdIndex;\n  }\n  getTotalAdsInBreak() {\n    return this.timing.totalAdsInBreak;\n  }\n  getAdRemainingMs() {\n    return this.timing.getRemainingAdMs();\n  }\n  isAdPlaying() {\n    return this.adBreak.inAdBreak && this.adPlayer.isAdPlaying();\n  }\n  isShowingAds() {\n    return this.adBreak.showAds;\n  }\n  getStreamType() {\n    const url = this.config.src.toLowerCase();\n    if (url.includes(\".m3u8\") || url.includes(\"/hls/\") || url.includes(\"application/vnd.apple.mpegurl\")) {\n      return \"hls\";\n    }\n    return \"other\";\n  }\n  shouldShowNativeControls() {\n    const streamType = this.getStreamType();\n    if (streamType === \"other\") {\n      return !(this.config.showCustomControls ?? false);\n    }\n    return !!(this.config.allowNativeHls && !(this.config.showCustomControls ?? false));\n  }\n  isLive() {\n    return this.hlsEngine.isLiveStream;\n  }\n  get videoElement() {\n    return this.video;\n  }\n  toggleMute() {\n    toggleMute(this.video, this.adPlayer, this.debug);\n  }\n  toggleFullscreen() {\n    return toggleFullscreen(this.video, this.debug);\n  }\n  isMuted() {\n    return isMuted(this.video, this.adPlayer);\n  }\n  setMuted(muted) {\n    setMuted(this.video, this.adPlayer, muted, this.debug);\n  }\n  setVolume(volume) {\n    setVolume(this.video, this.adPlayer, volume, this.debug);\n  }\n  getVolume() {\n    return getVolume(this.video, this.adPlayer);\n  }\n  isFullscreen() {\n    return isFullscreen();\n  }\n  resize() {\n    resizePlayer(this.video, this.adPlayer, this.debug);\n  }\n  // ───────────────────────────────────────────────────────────────\n  //  Destroy\n  // ───────────────────────────────────────────────────────────────\n  destroy() {\n    this.adBreak.stopContinuousFetching();\n    this.timing.destroy();\n    this.adBreak.clearPendingAdBreak();\n    this.placeholder.destroy();\n    if (this.timeUpdateHandler) {\n      this.video.removeEventListener(\"timeupdate\", this.timeUpdateHandler);\n      delete this.timeUpdateHandler;\n    }\n    if (this.endedHandler) {\n      this.video.removeEventListener(\"ended\", this.endedHandler);\n      delete this.endedHandler;\n    }\n    if (this.emptiedHandler) {\n      this.video.removeEventListener(\"emptied\", this.emptiedHandler);\n      delete this.emptiedHandler;\n    }\n    this.adConfig.destroyTracking();\n    this.hlsEngine.destroy();\n    this.adPlayer?.destroy();\n    if (this.palPlaybackStarted) {\n      this.palPlaybackStarted = false;\n      this.palNonce.sendPlaybackEnd();\n    }\n    this.palNonce.reset();\n    this.adBreak.adRequestQueue = [];\n    this.timing.consecutiveFailures = 0;\n  }\n};\n\n// src/patterns.ts\nvar HLS_EXTENSIONS = /\\.(m3u8)($|\\?)/i;\nvar HLS_PATHS = /\\/hls\\//i;\nvar DASH_EXTENSIONS = /\\.(mpd)($|\\?)/i;\nvar VIDEO_EXTENSIONS = /\\.(mp4|webm|ogg|avi|mov|wmv|flv|mkv)($|\\?)/i;\nvar AUDIO_EXTENSIONS = /\\.(mp3|wav|ogg|aac|wma|flac|m4a)($|\\?)/i;\nvar canPlay = {\n  hls: (url) => {\n    if (!url || typeof url !== \"string\") return false;\n    return HLS_EXTENSIONS.test(url) || HLS_PATHS.test(url);\n  },\n  dash: (url) => {\n    if (!url || typeof url !== \"string\") return false;\n    return DASH_EXTENSIONS.test(url);\n  },\n  video: (url) => {\n    if (!url || typeof url !== \"string\") return false;\n    return VIDEO_EXTENSIONS.test(url);\n  },\n  audio: (url) => {\n    if (!url || typeof url !== \"string\") return false;\n    return AUDIO_EXTENSIONS.test(url);\n  },\n  file: (url) => {\n    if (!url || typeof url !== \"string\") return false;\n    return VIDEO_EXTENSIONS.test(url) || AUDIO_EXTENSIONS.test(url);\n  }\n};\n\n// src/players/HlsPlayer.tsx\nvar HlsPlayer = class extends import_react.Component {\n  constructor() {\n    super(...arguments);\n    this.player = null;\n    this.mounted = false;\n    this.load = async () => {\n      if (!this.props.videoElement || !this.props.src) return;\n      try {\n        if (this.player) {\n          this.player.destroy();\n          this.player = null;\n        }\n        const config = {\n          src: this.props.src,\n          videoElement: this.props.videoElement\n        };\n        if (this.props.autoplay !== void 0)\n          config.autoplay = this.props.autoplay;\n        if (this.props.muted !== void 0) config.muted = this.props.muted;\n        if (this.props.lowLatencyMode !== void 0)\n          config.lowLatencyMode = this.props.lowLatencyMode;\n        if (this.props.allowNativeHls !== void 0)\n          config.allowNativeHls = this.props.allowNativeHls;\n        if (this.props.isLiveStream !== void 0)\n          config.isLiveStream = this.props.isLiveStream;\n        if (this.props.driftToleranceMs !== void 0)\n          config.driftToleranceMs = this.props.driftToleranceMs;\n        if (this.props.immediateManifestAds !== void 0)\n          config.immediateManifestAds = this.props.immediateManifestAds;\n        if (this.props.debugAdTiming !== void 0)\n          config.debugAdTiming = this.props.debugAdTiming;\n        if (this.props.showCustomControls !== void 0)\n          config.showCustomControls = this.props.showCustomControls;\n        if (this.props.onVolumeToggle !== void 0)\n          config.onVolumeToggle = this.props.onVolumeToggle;\n        if (this.props.onFullscreenToggle !== void 0)\n          config.onFullscreenToggle = this.props.onFullscreenToggle;\n        if (this.props.onControlClick !== void 0)\n          config.onControlClick = this.props.onControlClick;\n        if (this.props.licenseKey !== void 0)\n          config.licenseKey = this.props.licenseKey;\n        if (this.props.adFailsafeTimeoutMs !== void 0)\n          config.adFailsafeTimeoutMs = this.props.adFailsafeTimeoutMs;\n        if (this.props.minSegmentsBeforePlay !== void 0)\n          config.minSegmentsBeforePlay = this.props.minSegmentsBeforePlay;\n        if (this.props.ctvAdRequest !== void 0)\n          config.ctvAdRequest = this.props.ctvAdRequest;\n        this.player = new StormcloudVideoPlayer(config);\n        this.props.onMount?.(this);\n        await this.player.load();\n        if (this.mounted) {\n          this.props.onReady?.();\n        }\n      } catch (error) {\n        if (this.mounted) {\n          this.props.onError?.(error);\n        }\n      }\n    };\n    this.play = () => {\n      if (this.props.videoElement) {\n        const video = this.props.videoElement;\n        const hasValidSource = video.src || video.currentSrc && video.currentSrc !== \"\" || video.readyState >= 1;\n        if (hasValidSource) {\n          video.play()?.catch((error) => {\n            console.error(\"[HlsPlayer] Failed to play:\", error);\n            this.props.onError?.(error);\n          });\n          this.props.onPlay?.();\n        } else {\n          console.warn(\"[HlsPlayer] Cannot play: video has no valid source\");\n        }\n      }\n    };\n    this.pause = () => {\n      if (this.props.videoElement) {\n        this.props.videoElement.pause();\n        this.props.onPause?.();\n      }\n    };\n    this.stop = () => {\n      this.pause();\n      if (this.props.videoElement) {\n        this.props.videoElement.currentTime = 0;\n      }\n    };\n    this.seekTo = (seconds, keepPlaying) => {\n      if (this.props.videoElement) {\n        this.props.videoElement.currentTime = seconds;\n        if (!keepPlaying) {\n          this.pause();\n        }\n      }\n    };\n    this.setVolume = (volume) => {\n      if (this.props.videoElement) {\n        this.props.videoElement.volume = Math.max(0, Math.min(1, volume));\n      }\n    };\n    this.mute = () => {\n      if (this.props.videoElement) {\n        this.props.videoElement.muted = true;\n      }\n    };\n    this.unmute = () => {\n      if (this.props.videoElement) {\n        this.props.videoElement.muted = false;\n      }\n    };\n    this.setPlaybackRate = (rate) => {\n      if (this.props.videoElement && rate > 0) {\n        this.props.videoElement.playbackRate = rate;\n      }\n    };\n    this.getDuration = () => {\n      if (this.props.videoElement && isFinite(this.props.videoElement.duration)) {\n        return this.props.videoElement.duration;\n      }\n      return null;\n    };\n    this.getCurrentTime = () => {\n      if (this.props.videoElement && isFinite(this.props.videoElement.currentTime)) {\n        return this.props.videoElement.currentTime;\n      }\n      return null;\n    };\n    this.getSecondsLoaded = () => {\n      if (this.props.videoElement && this.props.videoElement.buffered.length > 0) {\n        return this.props.videoElement.buffered.end(\n          this.props.videoElement.buffered.length - 1\n        );\n      }\n      return null;\n    };\n    this.getInternalPlayer = (key = \"player\") => {\n      if (key === \"player\") return this.player;\n      if (key === \"video\") return this.props.videoElement;\n      if (key === \"hls\" && this.player) return this.player.hls;\n      return null;\n    };\n  }\n  componentDidMount() {\n    this.mounted = true;\n    this.load();\n  }\n  componentWillUnmount() {\n    this.mounted = false;\n    if (this.player) {\n      this.player.destroy();\n      this.player = null;\n    }\n  }\n  componentDidUpdate(prevProps) {\n    if (prevProps.src !== this.props.src) {\n      this.load();\n    }\n  }\n  render() {\n    return null;\n  }\n};\nHlsPlayer.displayName = \"HlsPlayer\";\nHlsPlayer.canPlay = canPlay.hls;\n","import { Component } from \"react\";\nimport { StormcloudVideoPlayer } from \"../player/StormcloudVideoPlayer\";\nimport type { StormcloudVideoPlayerConfig } from \"../types\";\nimport { canPlay } from \"../patterns\";\n\nexport interface HlsPlayerProps extends StormcloudVideoPlayerConfig {\n  onMount?: (player: any) => void;\n  onReady?: () => void;\n  onPlay?: () => void;\n  onPause?: () => void;\n  onEnded?: () => void;\n  onLoaded?: () => void;\n  onError?: (error: any) => void;\n}\n\nexport default class HlsPlayer extends Component<HlsPlayerProps> {\n  static displayName = \"HlsPlayer\";\n\n  static canPlay = canPlay.hls;\n\n  private player: StormcloudVideoPlayer | null = null;\n  private mounted = false;\n\n  componentDidMount() {\n    this.mounted = true;\n    this.load();\n  }\n\n  componentWillUnmount() {\n    this.mounted = false;\n    if (this.player) {\n      this.player.destroy();\n      this.player = null;\n    }\n  }\n\n  componentDidUpdate(prevProps: HlsPlayerProps) {\n    if (prevProps.src !== this.props.src) {\n      this.load();\n    }\n  }\n\n  load = async () => {\n    if (!this.props.videoElement || !this.props.src) return;\n\n    try {\n      if (this.player) {\n        this.player.destroy();\n        this.player = null;\n      }\n\n      const config: StormcloudVideoPlayerConfig = {\n        src: this.props.src,\n        videoElement: this.props.videoElement,\n      };\n\n      if (this.props.autoplay !== undefined)\n        config.autoplay = this.props.autoplay;\n      if (this.props.muted !== undefined) config.muted = this.props.muted;\n      if (this.props.lowLatencyMode !== undefined)\n        config.lowLatencyMode = this.props.lowLatencyMode;\n      if (this.props.allowNativeHls !== undefined)\n        config.allowNativeHls = this.props.allowNativeHls;\n      if (this.props.isLiveStream !== undefined)\n        config.isLiveStream = this.props.isLiveStream;\n      if (this.props.driftToleranceMs !== undefined)\n        config.driftToleranceMs = this.props.driftToleranceMs;\n      if (this.props.immediateManifestAds !== undefined)\n        config.immediateManifestAds = this.props.immediateManifestAds;\n      if (this.props.debugAdTiming !== undefined)\n        config.debugAdTiming = this.props.debugAdTiming;\n      if (this.props.showCustomControls !== undefined)\n        config.showCustomControls = this.props.showCustomControls;\n      if (this.props.onVolumeToggle !== undefined)\n        config.onVolumeToggle = this.props.onVolumeToggle;\n      if (this.props.onFullscreenToggle !== undefined)\n        config.onFullscreenToggle = this.props.onFullscreenToggle;\n      if (this.props.onControlClick !== undefined)\n        config.onControlClick = this.props.onControlClick;\n      if (this.props.licenseKey !== undefined)\n        config.licenseKey = this.props.licenseKey;\n      if (this.props.adFailsafeTimeoutMs !== undefined)\n        config.adFailsafeTimeoutMs = this.props.adFailsafeTimeoutMs;\n      if (this.props.minSegmentsBeforePlay !== undefined)\n        config.minSegmentsBeforePlay = this.props.minSegmentsBeforePlay;\n      if (this.props.ctvAdRequest !== undefined)\n        config.ctvAdRequest = this.props.ctvAdRequest;\n\n      this.player = new StormcloudVideoPlayer(config);\n\n      this.props.onMount?.(this);\n\n      await this.player.load();\n\n      if (this.mounted) {\n        this.props.onReady?.();\n      }\n    } catch (error) {\n      if (this.mounted) {\n        this.props.onError?.(error);\n      }\n    }\n  };\n\n  play = () => {\n    if (this.props.videoElement) {\n      const video = this.props.videoElement;\n      const hasValidSource =\n        video.src ||\n        (video.currentSrc && video.currentSrc !== \"\") ||\n        video.readyState >= 1;\n\n      if (hasValidSource) {\n        video.play()?.catch((error) => {\n          console.error(\"[HlsPlayer] Failed to play:\", error);\n          this.props.onError?.(error);\n        });\n        this.props.onPlay?.();\n      } else {\n        console.warn(\"[HlsPlayer] Cannot play: video has no valid source\");\n      }\n    }\n  };\n\n  pause = () => {\n    if (this.props.videoElement) {\n      this.props.videoElement.pause();\n      this.props.onPause?.();\n    }\n  };\n\n  stop = () => {\n    this.pause();\n    if (this.props.videoElement) {\n      this.props.videoElement.currentTime = 0;\n    }\n  };\n\n  seekTo = (seconds: number, keepPlaying?: boolean) => {\n    if (this.props.videoElement) {\n      this.props.videoElement.currentTime = seconds;\n      if (!keepPlaying) {\n        this.pause();\n      }\n    }\n  };\n\n  setVolume = (volume: number) => {\n    if (this.props.videoElement) {\n      this.props.videoElement.volume = Math.max(0, Math.min(1, volume));\n    }\n  };\n\n  mute = () => {\n    if (this.props.videoElement) {\n      this.props.videoElement.muted = true;\n    }\n  };\n\n  unmute = () => {\n    if (this.props.videoElement) {\n      this.props.videoElement.muted = false;\n    }\n  };\n\n  setPlaybackRate = (rate: number) => {\n    if (this.props.videoElement && rate > 0) {\n      this.props.videoElement.playbackRate = rate;\n    }\n  };\n\n  getDuration = (): number | null => {\n    if (this.props.videoElement && isFinite(this.props.videoElement.duration)) {\n      return this.props.videoElement.duration;\n    }\n    return null;\n  };\n\n  getCurrentTime = (): number | null => {\n    if (\n      this.props.videoElement &&\n      isFinite(this.props.videoElement.currentTime)\n    ) {\n      return this.props.videoElement.currentTime;\n    }\n    return null;\n  };\n\n  getSecondsLoaded = (): number | null => {\n    if (\n      this.props.videoElement &&\n      this.props.videoElement.buffered.length > 0\n    ) {\n      return this.props.videoElement.buffered.end(\n        this.props.videoElement.buffered.length - 1\n      );\n    }\n    return null;\n  };\n\n  getInternalPlayer = (key = \"player\") => {\n    if (key === \"player\") return this.player;\n    if (key === \"video\") return this.props.videoElement;\n    if (key === \"hls\" && this.player) return (this.player as any).hls;\n    return null;\n  };\n\n  render() {\n    return null;\n  }\n}\n","import type { AdController } from \"../types\";\nimport Hls from \"hls.js\";\n\ninterface VastMediaFile {\n  url: string;\n  type: string;\n  width: number;\n  height: number;\n  bitrate?: number | undefined;\n}\n\ninterface VastTrackingUrls {\n  impression: string[];\n  start: string[];\n  firstQuartile: string[];\n  midpoint: string[];\n  thirdQuartile: string[];\n  complete: string[];\n  mute: string[];\n  unmute: string[];\n  pause: string[];\n  resume: string[];\n  fullscreen: string[];\n  exitFullscreen: string[];\n  skip: string[];\n  error: string[];\n}\n\ninterface VastAd {\n  id: string;\n  title: string;\n  duration: number;\n  mediaFiles: VastMediaFile[];\n  trackingUrls: VastTrackingUrls;\n  clickThrough?: string | undefined;\n}\n\ntype VastParseResult =\n  | { type: \"inline\"; ad: VastAd }\n  | {\n      type: \"wrapper\";\n      vastAdTagUri: string;\n      trackingUrls: VastTrackingUrls;\n      clickThrough?: string | undefined;\n    }\n  | { type: \"empty\" };\n\nconst MAX_VAST_WRAPPER_DEPTH = 5;\n\nexport function createHlsAdPlayer(\n  contentVideo: HTMLVideoElement,\n  options?: {\n    continueLiveStreamDuringAds?: boolean;\n    licenseKey?: string;\n    mainHlsInstance?: Hls;\n  }\n): AdController {\n  let adPlaying = false;\n  let originalMutedState = false;\n  let originalVolume = Math.max(0, Math.min(1, contentVideo.volume || 1));\n  const listeners = new Map<string, Set<(payload?: any) => void>>();\n  const licenseKey = options?.licenseKey;\n  const mainHlsInstance = options?.mainHlsInstance;\n\n  let adVideoElement: HTMLVideoElement | undefined;\n  let adHls: Hls | undefined;\n  let adContainerEl: HTMLDivElement | undefined;\n  let currentAd: VastAd | undefined;\n  let podAds: VastAd[] = [];\n  let podIndex = 0;\n  let sessionId: string | undefined;\n  const preloadedAds = new Map<string, VastAd>();\n  const preloadingAds = new Map<string, Promise<void>>();\n  let destroyed = false;\n  let pendingTimeouts: number[] = [];\n\n  const STALL_TIMEOUT_MS = 4000;\n  const STALL_CHECK_INTERVAL_MS = 1000;\n  let stallWatchdogId: number | undefined;\n  let lastAdProgressTime = 0;\n  let lastAdProgressPosition = 0;\n\n  let trackingFired = {\n    impression: false,\n    start: false,\n    firstQuartile: false,\n    midpoint: false,\n    thirdQuartile: false,\n    complete: false,\n  };\n\n  function emit(event: string, payload?: any): void {\n    const set = listeners.get(event);\n    if (!set) return;\n    for (const fn of Array.from(set)) {\n      try {\n        fn(payload);\n      } catch (error) {\n        console.warn(\n          `[HlsAdPlayer] Error in event listener for ${event}:`,\n          error\n        );\n      }\n    }\n  }\n\n  function generateSessionId(): string {\n    return `session-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;\n  }\n\n  function fireTrackingPixels(urls: string[]): void {\n    if (!urls || urls.length === 0) return;\n\n    urls.forEach((url) => {\n      try {\n        let trackingUrl = url;\n\n        if (sessionId) {\n          trackingUrl = `${trackingUrl}${\n            trackingUrl.includes(\"?\") ? \"&\" : \"?\"\n          }session_id=${sessionId}`;\n        }\n\n        if (licenseKey) {\n          trackingUrl = `${trackingUrl}${\n            trackingUrl.includes(\"?\") ? \"&\" : \"?\"\n          }license_key=${licenseKey}`;\n        }\n\n        const img = new Image(1, 1);\n        img.src = trackingUrl;\n        console.log(`[HlsAdPlayer] Fired tracking pixel: ${trackingUrl}`);\n      } catch (error) {\n        console.warn(`[HlsAdPlayer] Error firing tracking pixel:`, error);\n      }\n    });\n  }\n\n  function getMainStreamQuality(): {\n    width: number;\n    height: number;\n    bitrate: number;\n  } | null {\n    if (!mainHlsInstance || !mainHlsInstance.levels) {\n      return null;\n    }\n\n    const currentLevel = mainHlsInstance.currentLevel;\n    if (currentLevel === -1 || !mainHlsInstance.levels[currentLevel]) {\n      const autoLevel = mainHlsInstance.loadLevel;\n      if (autoLevel !== -1 && mainHlsInstance.levels[autoLevel]) {\n        const level = mainHlsInstance.levels[autoLevel];\n        return {\n          width: level.width || 1920,\n          height: level.height || 1080,\n          bitrate: level.bitrate || 5000000,\n        };\n      }\n      return null;\n    }\n\n    const level = mainHlsInstance.levels[currentLevel];\n    return {\n      width: level.width || 1920,\n      height: level.height || 1080,\n      bitrate: level.bitrate || 5000000,\n    };\n  }\n\n  function selectBestMediaFile(mediaFiles: VastMediaFile[]): VastMediaFile {\n    if (mediaFiles.length === 0) {\n      throw new Error(\"No media files available\");\n    }\n\n    const firstFile = mediaFiles[0];\n    if (!firstFile) {\n      throw new Error(\"No media files available\");\n    }\n\n    if (mediaFiles.length === 1) {\n      return firstFile;\n    }\n\n    const mainQuality = getMainStreamQuality();\n    if (!mainQuality) {\n      console.log(\n        \"[HlsAdPlayer] No main stream quality info, using first media file\"\n      );\n      return firstFile;\n    }\n\n    console.log(\"[HlsAdPlayer] Main stream quality:\", mainQuality);\n\n    const scoredFiles = mediaFiles.map((file) => {\n      const widthDiff = Math.abs(file.width - mainQuality.width);\n      const heightDiff = Math.abs(file.height - mainQuality.height);\n      const resolutionDiff = widthDiff + heightDiff;\n\n      const fileBitrate = (file.bitrate || 5000) * 1000;\n      const bitrateDiff = Math.abs(fileBitrate - mainQuality.bitrate);\n\n      const score = resolutionDiff * 2 + bitrateDiff / 1000;\n\n      return { file, score, resolutionDiff, bitrateDiff };\n    });\n\n    scoredFiles.sort((a, b) => a.score - b.score);\n\n    const bestMatch = scoredFiles[0];\n    if (!bestMatch) {\n      console.log(\"[HlsAdPlayer] No best match found, using first media file\");\n      return firstFile;\n    }\n\n    console.log(\"[HlsAdPlayer] Selected media file:\", {\n      url: bestMatch.file.url,\n      resolution: `${bestMatch.file.width}x${bestMatch.file.height}`,\n      bitrate: bestMatch.file.bitrate,\n      score: bestMatch.score,\n      resolutionDiff: bestMatch.resolutionDiff,\n      bitrateDiff: bestMatch.bitrateDiff,\n    });\n\n    return bestMatch.file;\n  }\n\n  function isHlsMediaFile(mediaFile: VastMediaFile): boolean {\n    const type = mediaFile.type.toLowerCase();\n    const url = mediaFile.url.toLowerCase();\n    return (\n      type === \"application/x-mpegurl\" ||\n      type === \"application/vnd.apple.mpegurl\" ||\n      type.includes(\"mpegurl\") ||\n      url.includes(\".m3u8\")\n    );\n  }\n\n  function isProgressiveMediaFile(mediaFile: VastMediaFile): boolean {\n    const type = mediaFile.type.toLowerCase();\n    const url = mediaFile.url.toLowerCase();\n    return (\n      type.startsWith(\"video/\") ||\n      url.endsWith(\".mp4\") ||\n      url.includes(\".mp4?\")\n    );\n  }\n\n  function createEmptyTrackingUrls(): VastTrackingUrls {\n    return {\n      impression: [],\n      start: [],\n      firstQuartile: [],\n      midpoint: [],\n      thirdQuartile: [],\n      complete: [],\n      mute: [],\n      unmute: [],\n      pause: [],\n      resume: [],\n      fullscreen: [],\n      exitFullscreen: [],\n      skip: [],\n      error: [],\n    };\n  }\n\n  function extractTrackingUrls(scope: Document | Element): VastTrackingUrls {\n    const trackingUrls = createEmptyTrackingUrls();\n\n    scope.querySelectorAll(\"Impression\").forEach((el) => {\n      const url = el.textContent?.trim();\n      if (url) trackingUrls.impression.push(url);\n    });\n\n    scope.querySelectorAll(\"Tracking\").forEach((el) => {\n      const event = el.getAttribute(\"event\");\n      const url = el.textContent?.trim();\n      if (event && url) {\n        const eventKey = event as keyof VastTrackingUrls;\n        if (trackingUrls[eventKey]) {\n          trackingUrls[eventKey].push(url);\n        }\n      }\n    });\n\n    scope.querySelectorAll(\"Error\").forEach((el) => {\n      const url = el.textContent?.trim();\n      if (url) trackingUrls.error.push(url);\n    });\n\n    return trackingUrls;\n  }\n\n  function mergeTrackingUrls(\n    target: VastTrackingUrls,\n    source: VastTrackingUrls\n  ): VastTrackingUrls {\n    (Object.keys(target) as Array<keyof VastTrackingUrls>).forEach((key) => {\n      if (source[key] && source[key].length > 0) {\n        target[key] = target[key].concat(source[key]);\n      }\n    });\n    return target;\n  }\n\n  function parseVastXml(xmlString: string): VastParseResult {\n    try {\n      const parser = new DOMParser();\n      const xmlDoc = parser.parseFromString(xmlString, \"text/xml\");\n\n      const parserError = xmlDoc.querySelector(\"parsererror\");\n      if (parserError) {\n        console.error(\n          \"[HlsAdPlayer] XML parsing error (malformed VAST XML):\",\n          parserError.textContent\n        );\n        return { type: \"empty\" };\n      }\n\n      const adElement = xmlDoc.querySelector(\"Ad\");\n      if (!adElement) {\n        console.warn(\"[HlsAdPlayer] No Ad element found in VAST XML\");\n        return { type: \"empty\" };\n      }\n\n      const adId = adElement.getAttribute(\"id\") || \"unknown\";\n      const title = xmlDoc.querySelector(\"AdTitle\")?.textContent || \"Ad\";\n\n      const clickThrough = xmlDoc\n        .querySelector(\"ClickThrough\")\n        ?.textContent?.trim();\n\n      const wrapperUri = xmlDoc\n        .querySelector(\"VASTAdTagURI\")\n        ?.textContent?.trim();\n      if (wrapperUri) {\n        console.log(\n          `[HlsAdPlayer] VAST wrapper detected, following VASTAdTagURI: ${wrapperUri}`\n        );\n        return {\n          type: \"wrapper\",\n          vastAdTagUri: wrapperUri,\n          trackingUrls: extractTrackingUrls(xmlDoc),\n          clickThrough,\n        };\n      }\n\n      const isNoAdAvailable =\n        adId === \"empty\" ||\n        title.toLowerCase().includes(\"no ad available\") ||\n        title.toLowerCase() === \"no ad available\";\n\n      const durationText =\n        xmlDoc.querySelector(\"Duration\")?.textContent || \"00:00:30\";\n      const durationParts = durationText.split(\":\");\n      const duration =\n        parseInt(durationParts[0] || \"0\", 10) * 3600 +\n        parseInt(durationParts[1] || \"0\", 10) * 60 +\n        parseInt(durationParts[2] || \"0\", 10);\n\n      const mediaFileElements = xmlDoc.querySelectorAll(\"MediaFile\");\n      const mediaFiles: VastMediaFile[] = [];\n\n      console.log(\n        `[HlsAdPlayer] Found ${mediaFileElements.length} MediaFile element(s) in VAST XML`\n      );\n\n      mediaFileElements.forEach((mf, index) => {\n        const type = mf.getAttribute(\"type\") || \"\";\n        const url = mf.textContent?.trim() || \"\";\n        const width = mf.getAttribute(\"width\") || \"\";\n        const height = mf.getAttribute(\"height\") || \"\";\n\n        console.log(\n          `[HlsAdPlayer] MediaFile ${index}: type=\"${type}\", url=\"${url}\", width=\"${width}\", height=\"${height}\"`\n        );\n\n        const mediaFile: VastMediaFile = {\n          url,\n          type,\n          width: parseInt(width || \"1920\", 10),\n          height: parseInt(height || \"1080\", 10),\n          bitrate: undefined,\n        };\n\n        if (!url) {\n          console.warn(`[HlsAdPlayer] MediaFile ${index} has empty URL`);\n          return;\n        }\n\n        const bitrateAttr = mf.getAttribute(\"bitrate\");\n        const bitrateValue = bitrateAttr\n          ? parseInt(bitrateAttr, 10)\n          : undefined;\n        mediaFile.bitrate =\n          bitrateValue && bitrateValue > 0 ? bitrateValue : undefined;\n\n        if (isHlsMediaFile(mediaFile) || isProgressiveMediaFile(mediaFile)) {\n          mediaFiles.push(mediaFile);\n          console.log(\n            `[HlsAdPlayer] Added ${isHlsMediaFile(mediaFile) ? \"HLS\" : \"progressive\"} MediaFile: ${url}`\n          );\n        } else {\n          console.log(\n            `[HlsAdPlayer] MediaFile ${index} ignored (type=\"${type}\" is not supported)`\n          );\n        }\n      });\n\n      if (mediaFiles.length === 0) {\n        if (isNoAdAvailable) {\n          console.warn(\n            \"[HlsAdPlayer] No ads available (VAST response indicates no ads)\"\n          );\n        } else {\n          console.warn(\"[HlsAdPlayer] No supported media files found in VAST XML\");\n        }\n        return { type: \"empty\" };\n      }\n\n      return {\n        type: \"inline\",\n        ad: {\n          id: adId,\n          title,\n          duration,\n          mediaFiles,\n          trackingUrls: extractTrackingUrls(xmlDoc),\n          clickThrough,\n        },\n      };\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Error parsing VAST XML:\", error);\n      return { type: \"empty\" };\n    }\n  }\n\n  function parseAdElement(adElement: Element): VastParseResult {\n    try {\n      const adId = adElement.getAttribute(\"id\") || \"unknown\";\n      const title = adElement.querySelector(\"AdTitle\")?.textContent || \"Ad\";\n\n      const clickThrough = adElement\n        .querySelector(\"ClickThrough\")\n        ?.textContent?.trim();\n\n      const wrapperUri = adElement\n        .querySelector(\"VASTAdTagURI\")\n        ?.textContent?.trim();\n      if (wrapperUri) {\n        return {\n          type: \"wrapper\",\n          vastAdTagUri: wrapperUri,\n          trackingUrls: extractTrackingUrls(adElement),\n          clickThrough,\n        };\n      }\n\n      const isNoAdAvailable =\n        adId === \"empty\" ||\n        title.toLowerCase().includes(\"no ad available\") ||\n        title.toLowerCase() === \"no ad available\";\n\n      const durationText =\n        adElement.querySelector(\"Duration\")?.textContent || \"00:00:30\";\n      const durationParts = durationText.split(\":\");\n      const duration =\n        parseInt(durationParts[0] || \"0\", 10) * 3600 +\n        parseInt(durationParts[1] || \"0\", 10) * 60 +\n        parseInt(durationParts[2] || \"0\", 10);\n\n      const mediaFileElements = adElement.querySelectorAll(\"MediaFile\");\n      const mediaFiles: VastMediaFile[] = [];\n\n      mediaFileElements.forEach((mf) => {\n        const type = mf.getAttribute(\"type\") || \"\";\n        const url = mf.textContent?.trim() || \"\";\n        const width = mf.getAttribute(\"width\") || \"\";\n        const height = mf.getAttribute(\"height\") || \"\";\n\n        if (!url) return;\n\n        const bitrateAttr = mf.getAttribute(\"bitrate\");\n        const bitrateValue = bitrateAttr ? parseInt(bitrateAttr, 10) : undefined;\n\n        const mediaFile: VastMediaFile = {\n          url,\n          type,\n          width: parseInt(width || \"1920\", 10),\n          height: parseInt(height || \"1080\", 10),\n          bitrate: bitrateValue && bitrateValue > 0 ? bitrateValue : undefined,\n        };\n\n        if (isHlsMediaFile(mediaFile) || isProgressiveMediaFile(mediaFile)) {\n          mediaFiles.push(mediaFile);\n        }\n      });\n\n      if (mediaFiles.length === 0) {\n        if (isNoAdAvailable) {\n          console.warn(\n            \"[HlsAdPlayer] Pod <Ad> indicates no ad available\"\n          );\n        } else {\n          console.warn(\"[HlsAdPlayer] No supported media files in pod <Ad>\");\n        }\n        return { type: \"empty\" };\n      }\n\n      return {\n        type: \"inline\",\n        ad: {\n          id: adId,\n          title,\n          duration,\n          mediaFiles,\n          trackingUrls: extractTrackingUrls(adElement),\n          clickThrough,\n        },\n      };\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Error parsing pod <Ad> element:\", error);\n      return { type: \"empty\" };\n    }\n  }\n\n  async function fetchVastXml(\n    vastTagUrl: string,\n    credentials: RequestCredentials = \"include\"\n  ): Promise<string> {\n    const requestVast = (creds: RequestCredentials) =>\n      fetch(vastTagUrl, {\n        mode: \"cors\",\n        credentials: creds,\n        headers: {\n          \"Accept\": \"application/xml, text/xml, */*\",\n        },\n        referrerPolicy: \"no-referrer-when-downgrade\",\n      });\n\n    let response: Response;\n    try {\n      response = await requestVast(credentials);\n    } catch (error) {\n      if (credentials !== \"omit\") {\n        console.warn(\n          `[HlsAdPlayer] VAST fetch failed with credentials=\"${credentials}\", retrying without credentials:`,\n          error\n        );\n        response = await requestVast(\"omit\");\n      } else {\n        throw error;\n      }\n    }\n\n    if (!response.ok) {\n      throw new Error(`Failed to fetch VAST: ${response.statusText}`);\n    }\n    return response.text();\n  }\n\n  async function fetchAndParseVastAd(\n    vastTagUrl: string,\n    depth = 0,\n    accumulatedTracking: VastTrackingUrls = createEmptyTrackingUrls()\n  ): Promise<VastAd | null> {\n    const vastXml = await fetchVastXml(\n      vastTagUrl,\n      depth === 0 ? \"include\" : \"omit\"\n    );\n    console.log(\"[HlsAdPlayer] VAST XML received\");\n    console.log(\n      \"[HlsAdPlayer] VAST XML content (first 2000 chars):\",\n      vastXml.substring(0, 2000)\n    );\n\n    const parsed = parseVastXml(vastXml);\n\n    if (parsed.type === \"empty\") {\n      return null;\n    }\n\n    if (parsed.type === \"wrapper\") {\n      if (depth >= MAX_VAST_WRAPPER_DEPTH) {\n        console.warn(\n          `[HlsAdPlayer] VAST wrapper depth limit (${MAX_VAST_WRAPPER_DEPTH}) reached, aborting redirect chain`\n        );\n        return null;\n      }\n\n      mergeTrackingUrls(accumulatedTracking, parsed.trackingUrls);\n      return fetchAndParseVastAd(\n        parsed.vastAdTagUri,\n        depth + 1,\n        accumulatedTracking\n      );\n    }\n\n    mergeTrackingUrls(parsed.ad.trackingUrls, accumulatedTracking);\n    return parsed.ad;\n  }\n\n  async function fetchAndParsePod(vastTagUrl: string): Promise<VastAd[]> {\n    const vastXml = await fetchVastXml(vastTagUrl);\n    console.log(\"[HlsAdPlayer] Pod VAST XML received\");\n\n    const parser = new DOMParser();\n    const xmlDoc = parser.parseFromString(vastXml, \"text/xml\");\n\n    if (xmlDoc.querySelector(\"parsererror\")) {\n      console.error(\"[HlsAdPlayer] Pod VAST XML parsing error (malformed)\");\n      return [];\n    }\n\n    const adElements = Array.from(xmlDoc.querySelectorAll(\"Ad\"));\n    if (adElements.length === 0) {\n      console.warn(\"[HlsAdPlayer] No <Ad> elements found in pod VAST response\");\n      return [];\n    }\n\n    adElements.sort((a, b) => {\n      const aSeq = parseInt(a.getAttribute(\"sequence\") || \"\", 10);\n      const bSeq = parseInt(b.getAttribute(\"sequence\") || \"\", 10);\n      const aVal = Number.isFinite(aSeq) ? aSeq : Number.MAX_SAFE_INTEGER;\n      const bVal = Number.isFinite(bSeq) ? bSeq : Number.MAX_SAFE_INTEGER;\n      return aVal - bVal;\n    });\n\n    const ads: VastAd[] = [];\n    for (const adElement of adElements) {\n      const parsed = parseAdElement(adElement);\n\n      if (parsed.type === \"inline\") {\n        ads.push(parsed.ad);\n      } else if (parsed.type === \"wrapper\") {\n        try {\n          const resolved = await fetchAndParseVastAd(\n            parsed.vastAdTagUri,\n            1,\n            parsed.trackingUrls\n          );\n          if (resolved) {\n            ads.push(resolved);\n          }\n        } catch (error) {\n          console.warn(\n            \"[HlsAdPlayer] Failed to resolve wrapper <Ad> in pod:\",\n            error\n          );\n        }\n      }\n    }\n\n    console.log(`[HlsAdPlayer] Parsed ${ads.length} ad(s) from pod VAST response`);\n    return ads;\n  }\n\n  function createAdVideoElement(): HTMLVideoElement {\n    const video = document.createElement(\"video\");\n    video.style.position = \"absolute\";\n    video.style.left = \"0\";\n    video.style.top = \"0\";\n    video.style.width = \"100%\";\n    video.style.height = \"100%\";\n    video.style.objectFit = \"contain\";\n    video.style.backgroundColor = \"#000\";\n    video.playsInline = true;\n    video.muted = false;\n\n    video.volume = 1.0;\n    console.log(\n      `[HlsAdPlayer] Created ad video element with volume ${video.volume}`\n    );\n\n    return video;\n  }\n\n  function setupAdEventListeners(): void {\n    if (!adVideoElement || !currentAd) return;\n\n    adVideoElement.addEventListener(\"timeupdate\", () => {\n      if (!currentAd || !adVideoElement) return;\n\n      noteAdProgress();\n\n      const progress = adVideoElement.currentTime / currentAd.duration;\n\n      if (progress >= 0.25 && !trackingFired.firstQuartile) {\n        trackingFired.firstQuartile = true;\n        fireTrackingPixels(currentAd.trackingUrls.firstQuartile);\n      }\n\n      if (progress >= 0.5 && !trackingFired.midpoint) {\n        trackingFired.midpoint = true;\n        fireTrackingPixels(currentAd.trackingUrls.midpoint);\n      }\n\n      if (progress >= 0.75 && !trackingFired.thirdQuartile) {\n        trackingFired.thirdQuartile = true;\n        fireTrackingPixels(currentAd.trackingUrls.thirdQuartile);\n      }\n    });\n\n    adVideoElement.addEventListener(\"playing\", () => {\n      startStallWatchdog();\n      if (!currentAd || trackingFired.start) return;\n      trackingFired.start = true;\n      fireTrackingPixels(currentAd.trackingUrls.start);\n      console.log(\"[HlsAdPlayer] Ad started playing\");\n    });\n\n    adVideoElement.addEventListener(\"ended\", () => {\n      if (!currentAd || trackingFired.complete) return;\n      trackingFired.complete = true;\n      fireTrackingPixels(currentAd.trackingUrls.complete);\n      console.log(\"[HlsAdPlayer] Ad completed\");\n\n      if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n        return;\n      }\n\n      handleAdComplete();\n    });\n\n    adVideoElement.addEventListener(\"error\", (e) => {\n      if (!adPlaying) return;\n      console.error(\"[HlsAdPlayer] Ad video error:\", e);\n      if (currentAd) {\n        fireTrackingPixels(currentAd.trackingUrls.error);\n      }\n\n      if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n        return;\n      }\n\n      handleAdError();\n    });\n\n    adVideoElement.addEventListener(\"volumechange\", () => {\n      if (!currentAd) return;\n      if (adVideoElement!.muted) {\n        fireTrackingPixels(currentAd.trackingUrls.mute);\n      } else {\n        fireTrackingPixels(currentAd.trackingUrls.unmute);\n      }\n    });\n\n    adVideoElement.addEventListener(\"pause\", () => {\n      if (currentAd && !adVideoElement!.ended) {\n        fireTrackingPixels(currentAd.trackingUrls.pause);\n      }\n    });\n\n    adVideoElement.addEventListener(\"play\", () => {\n      if (currentAd && adVideoElement!.currentTime > 0) {\n        fireTrackingPixels(currentAd.trackingUrls.resume);\n      }\n    });\n  }\n\n  function setAdPlayingFlag(isPlaying: boolean): void {\n    if (isPlaying) {\n      contentVideo.dataset.stormcloudAdPlaying = \"true\";\n    } else {\n      delete contentVideo.dataset.stormcloudAdPlaying;\n    }\n  }\n\n  function resetQuartileTracking(preserveImpression: boolean): void {\n    trackingFired = {\n      impression: preserveImpression ? trackingFired.impression : false,\n      start: false,\n      firstQuartile: false,\n      midpoint: false,\n      thirdQuartile: false,\n      complete: false,\n    };\n  }\n\n  function loadCurrentAdMedia(): void {\n    if (!adVideoElement || !currentAd) {\n      throw new Error(\"No ad video element or ad to load\");\n    }\n\n    const mediaFile = selectBestMediaFile(currentAd.mediaFiles);\n    if (!mediaFile) {\n      throw new Error(\"No media file available for ad\");\n    }\n\n    const isHlsAd = isHlsMediaFile(mediaFile);\n    console.log(\n      `[HlsAdPlayer] Loading ${isHlsAd ? \"HLS\" : \"progressive\"} ad (pod ${podIndex + 1}/${podAds.length || 1}) from: ${mediaFile.url}`\n    );\n\n    if (isHlsAd && Hls.isSupported()) {\n      if (adHls) {\n        adHls.destroy();\n      }\n\n      adHls = new Hls({\n        enableWorker: true,\n        lowLatencyMode: false,\n      });\n\n      adHls.loadSource(mediaFile.url);\n      adHls.attachMedia(adVideoElement);\n\n      adHls.on(Hls.Events.MANIFEST_PARSED, () => {\n        console.log(\"[HlsAdPlayer] HLS manifest parsed, starting playback\");\n        adVideoElement!.play().catch((error) => {\n          console.error(\"[HlsAdPlayer] Error starting ad playback:\", error);\n          handleAdError();\n        });\n      });\n\n      adHls.on(Hls.Events.ERROR, (_event, data) => {\n        console.error(\"[HlsAdPlayer] HLS error:\", data);\n        if (data.fatal) {\n          handleAdError();\n        }\n      });\n    } else if (\n      isHlsAd &&\n      adVideoElement.canPlayType(\"application/vnd.apple.mpegurl\")\n    ) {\n      adVideoElement.src = mediaFile.url;\n      adVideoElement.play().catch((error) => {\n        console.error(\"[HlsAdPlayer] Error starting ad playback:\", error);\n        handleAdError();\n      });\n    } else if (!isHlsAd && isProgressiveMediaFile(mediaFile)) {\n      if (adHls) {\n        adHls.destroy();\n        adHls = undefined;\n      }\n\n      adVideoElement.src = mediaFile.url;\n      adVideoElement.load();\n      adVideoElement.play().catch((error) => {\n        console.error(\"[HlsAdPlayer] Error starting progressive ad playback:\", error);\n        handleAdError();\n      });\n    } else {\n      throw new Error(`Unsupported ad media file type: ${mediaFile.type}`);\n    }\n  }\n\n  function advanceToNextPodAd(): boolean {\n    if (podIndex >= podAds.length - 1) {\n      return false;\n    }\n\n    podIndex++;\n    currentAd = podAds[podIndex];\n    resetQuartileTracking(false);\n\n    if (currentAd) {\n      fireTrackingPixels(currentAd.trackingUrls.impression);\n      trackingFired.impression = true;\n      console.log(\n        `[HlsAdPlayer] Advancing to next pod ad (${podIndex + 1}/${podAds.length}): ${currentAd.title}, duration: ${currentAd.duration}s`\n      );\n    }\n\n    try {\n      loadCurrentAdMedia();\n      emit(\"pod_ad_started\", { index: podIndex, total: podAds.length });\n      return true;\n    } catch (error) {\n      console.error(\"[HlsAdPlayer] Failed to load next pod ad:\", error);\n      return false;\n    }\n  }\n\n  function clearStallWatchdog(): void {\n    if (stallWatchdogId != null) {\n      clearInterval(stallWatchdogId);\n      stallWatchdogId = undefined;\n    }\n  }\n\n  function noteAdProgress(): void {\n    lastAdProgressTime = Date.now();\n    if (adVideoElement) {\n      lastAdProgressPosition = adVideoElement.currentTime;\n    }\n  }\n\n  function handleAdStall(): void {\n    console.warn(\n      \"[HlsAdPlayer] Ad playback stalled (no progress) - recovering to avoid a blank frame\"\n    );\n    clearStallWatchdog();\n\n    if (currentAd) {\n      fireTrackingPixels(currentAd.trackingUrls.error);\n    }\n\n    if (podIndex < podAds.length - 1 && advanceToNextPodAd()) {\n      return;\n    }\n\n    handleAdError();\n  }\n\n  function startStallWatchdog(): void {\n    clearStallWatchdog();\n    noteAdProgress();\n    stallWatchdogId = window.setInterval(() => {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n\n      if (adVideoElement.currentTime > lastAdProgressPosition + 0.05) {\n        noteAdProgress();\n        return;\n      }\n\n      if (adVideoElement.paused) {\n        noteAdProgress();\n        return;\n      }\n\n      if (Date.now() - lastAdProgressTime >= STALL_TIMEOUT_MS) {\n        handleAdStall();\n      }\n    }, STALL_CHECK_INTERVAL_MS) as unknown as number;\n  }\n\n  function releaseAdDecoder(): void {\n    if (adHls) {\n      adHls.destroy();\n      adHls = undefined;\n    }\n\n    if (adVideoElement) {\n      adVideoElement.pause();\n      adVideoElement.removeAttribute(\"src\");\n      try {\n        adVideoElement.load();\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] adVideoElement.load() threw after src removal:\", error);\n      }\n      adVideoElement.remove();\n      adVideoElement = undefined;\n    }\n\n    if (adContainerEl) {\n      adContainerEl.style.display = \"none\";\n      adContainerEl.style.pointerEvents = \"none\";\n    }\n  }\n\n  function handleAdComplete(): void {\n    console.log(\"[HlsAdPlayer] Handling ad completion\");\n    clearStallWatchdog();\n    adPlaying = false;\n    setAdPlayingFlag(false);\n\n    contentVideo.muted = true;\n\n    releaseAdDecoder();\n\n    if (!options?.continueLiveStreamDuringAds) {\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n    }\n    \n    if (options?.continueLiveStreamDuringAds) {\n      if (contentVideo.paused) {\n        console.log(\"[HlsAdPlayer] Content video paused in live mode, resuming playback\");\n        contentVideo.play().catch((error) => {\n          console.error(\"[HlsAdPlayer] Error resuming content playback in live mode:\", error);\n        });\n      } else {\n        console.log(\"[HlsAdPlayer] Content video already playing in live mode\");\n      }\n    }\n\n    emit(\"content_resume\");\n  }\n\n  function handleAdError(): void {\n    console.log(\"[HlsAdPlayer] Handling ad error\");\n    clearStallWatchdog();\n    adPlaying = false;\n    setAdPlayingFlag(false);\n\n    contentVideo.muted = true;\n\n    releaseAdDecoder();\n\n    if (!options?.continueLiveStreamDuringAds) {\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n    }\n\n    emit(\"ad_error\");\n  }\n\n  return {\n    initialize() {\n      console.log(\"[HlsAdPlayer] Initializing\");\n\n      if (!adContainerEl) {\n        const container = document.createElement(\"div\");\n        container.style.position = \"absolute\";\n        container.style.left = \"0\";\n        container.style.top = \"0\";\n        container.style.right = \"0\";\n        container.style.bottom = \"0\";\n        container.style.display = \"none\";\n        container.style.alignItems = \"center\";\n        container.style.justifyContent = \"center\";\n        container.style.pointerEvents = \"none\";\n        container.style.zIndex = \"30\";\n        container.style.backgroundColor = \"#000\";\n\n        contentVideo.parentElement?.appendChild(container);\n        adContainerEl = container;\n      }\n    },\n\n    async requestAds(vastTagUrl: string) {\n      console.log(\"[HlsAdPlayer] Requesting ads:\", vastTagUrl);\n\n      if (adPlaying) {\n        console.warn(\n          \"[HlsAdPlayer] Cannot request new ads while an ad is playing\"\n        );\n        return Promise.reject(new Error(\"Ad already playing\"));\n      }\n\n      try {\n        sessionId = generateSessionId();\n        let ads: VastAd[] = [];\n\n        if (preloadedAds.has(vastTagUrl)) {\n          const preloaded = preloadedAds.get(vastTagUrl);\n          preloadedAds.delete(vastTagUrl);\n          if (preloaded) {\n            ads = [preloaded];\n          }\n          console.log(\n            \"[HlsAdPlayer] Using preloaded VAST response:\",\n            vastTagUrl\n          );\n        } else {\n          ads = await fetchAndParsePod(vastTagUrl);\n        }\n\n        if (!ads.length) {\n          console.warn(\"[HlsAdPlayer] No ads available from VAST response\");\n          emit(\"ad_error\");\n          return Promise.reject(new Error(\"No ads available from VAST response\"));\n        }\n\n        podAds = ads;\n        podIndex = 0;\n        currentAd = ads[0];\n        console.log(\n          `[HlsAdPlayer] Pod parsed: ${ads.length} ad(s), first=\"${currentAd?.title}\", duration=${currentAd?.duration}s`\n        );\n\n        if (currentAd) {\n          fireTrackingPixels(currentAd.trackingUrls.impression);\n          trackingFired.impression = true;\n        }\n\n        return Promise.resolve();\n      } catch (error) {\n        console.error(\"[HlsAdPlayer] Error requesting ads:\", error);\n        emit(\"ad_error\");\n        return Promise.reject(error);\n      }\n    },\n    async play() {\n      if (!currentAd) {\n        console.warn(\n          \"[HlsAdPlayer] Cannot play: No ad loaded (no ads available)\"\n        );\n        return Promise.reject(new Error(\"No ad loaded\"));\n      }\n\n      console.log(\"[HlsAdPlayer] Starting ad playback\");\n\n      try {\n        if (!adVideoElement) {\n          adVideoElement = createAdVideoElement();\n          adContainerEl?.appendChild(adVideoElement);\n          setupAdEventListeners();\n        }\n\n        resetQuartileTracking(true);\n\n        const contentVolume = contentVideo.volume;\n        originalVolume = Math.max(\n          0,\n          Math.min(1, contentVolume || originalVolume)\n        );\n\n        if (!options?.continueLiveStreamDuringAds) {\n          contentVideo.pause();\n          console.log(\"[HlsAdPlayer] Content paused (VOD mode)\");\n        } else {\n          console.log(\"[HlsAdPlayer] Content continues (Live mode)\");\n        }\n\n        console.log(\"[HlsAdPlayer] FORCE MUTING main video\");\n        contentVideo.muted = true;\n        adPlaying = true;\n        setAdPlayingFlag(true);\n\n        if (adVideoElement) {\n          adVideoElement.volume = Math.max(0, Math.min(1, originalVolume));\n          adVideoElement.muted = originalMutedState;\n          console.log(\n            `[HlsAdPlayer] Set ad video volume to ${adVideoElement.volume}, muted: ${adVideoElement.muted}, originalMutedState: ${originalMutedState}, contentVolume: ${contentVolume}`\n          );\n        }\n\n        if (adContainerEl) {\n          adContainerEl.style.display = \"flex\";\n          adContainerEl.style.pointerEvents = \"auto\";\n        }\n\n        emit(\"content_pause\");\n\n        loadCurrentAdMedia();\n\n        return Promise.resolve();\n      } catch (error) {\n        console.error(\"[HlsAdPlayer] Error playing ad:\", error);\n        handleAdError();\n        return Promise.reject(error);\n      }\n    },\n    pause() {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n\n      try {\n        if (adVideoElement && !adVideoElement.paused) {\n          adVideoElement.pause();\n        }\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] Error pausing ad:\", error);\n      }\n    },\n    resume() {\n      if (!adPlaying || !adVideoElement) {\n        return;\n      }\n\n      try {\n        if (adVideoElement && adVideoElement.paused) {\n          adVideoElement.play().catch(() => {});\n        }\n      } catch (error) {\n        console.warn(\"[HlsAdPlayer] Error resuming ad:\", error);\n      }\n    },\n    async stop() {\n      console.log(\"[HlsAdPlayer] Stopping ad\");\n      clearStallWatchdog();\n      adPlaying = false;\n      setAdPlayingFlag(false);\n\n      const previousMutedState = contentVideo.muted;\n      contentVideo.muted = originalMutedState;\n      contentVideo.volume = Math.max(0, Math.min(1, originalVolume));\n      console.log(\n        `[HlsAdPlayer] Restored mute state on stop: ${previousMutedState} -> ${originalMutedState}, volume: ${contentVideo.volume}`\n      );\n\n      releaseAdDecoder();\n\n      contentVideo.style.visibility = \"visible\";\n      contentVideo.style.opacity = \"1\";\n\n      if (options?.continueLiveStreamDuringAds) {\n        if (contentVideo.paused) {\n          console.log(\"[HlsAdPlayer] Content video paused in live mode, resuming playback on stop\");\n          contentVideo.play().catch((error) => {\n            console.error(\"[HlsAdPlayer] Error resuming content playback in live mode on stop:\", error);\n          });\n        }\n      }\n\n      currentAd = undefined;\n      podAds = [];\n      podIndex = 0;\n    },\n\n    destroy() {\n      console.log(\"[HlsAdPlayer] Destroying\");\n      destroyed = true;\n      clearStallWatchdog();\n\n      for (const timeoutId of pendingTimeouts) {\n        clearTimeout(timeoutId);\n      }\n      pendingTimeouts = [];\n      \n      adPlaying = false;\n      setAdPlayingFlag(false);\n      contentVideo.muted = originalMutedState;\n      contentVideo.volume = Math.max(0, Math.min(1, originalVolume));\n\n      releaseAdDecoder();\n\n      if (adContainerEl?.parentElement) {\n        adContainerEl.parentElement.removeChild(adContainerEl);\n      }\n\n      adContainerEl = undefined;\n      currentAd = undefined;\n      podAds = [];\n      podIndex = 0;\n      listeners.clear();\n      preloadedAds.clear();\n      preloadingAds.clear();\n    },\n\n    isAdPlaying() {\n      return adPlaying;\n    },\n\n    resize(width: number, height: number) {\n      console.log(`[HlsAdPlayer] Resizing to ${width}x${height}`);\n\n      if (adContainerEl) {\n        adContainerEl.style.width = `${width}px`;\n        adContainerEl.style.height = `${height}px`;\n      }\n\n      if (adVideoElement) {\n        adVideoElement.style.width = `${width}px`;\n        adVideoElement.style.height = `${height}px`;\n      }\n    },\n\n    on(event: string, listener: (payload?: any) => void) {\n      if (!listeners.has(event)) listeners.set(event, new Set());\n      listeners.get(event)!.add(listener);\n    },\n\n    off(event: string, listener: (payload?: any) => void) {\n      listeners.get(event)?.delete(listener);\n    },\n\n    updateOriginalMutedState(muted: boolean, volume?: number) {\n      const nextVolume =\n        typeof volume === \"number\" && !Number.isNaN(volume)\n          ? Math.max(0, Math.min(1, volume))\n          : originalVolume;\n      console.log(\n        `[HlsAdPlayer] updateOriginalMutedState called: { muted: ${originalMutedState} -> ${muted}, volume: ${originalVolume} -> ${nextVolume} }`\n      );\n      originalMutedState = muted;\n      originalVolume = nextVolume;\n    },\n\n    getOriginalMutedState() {\n      return originalMutedState;\n    },\n    getOriginalVolume() {\n      return originalVolume;\n    },\n\n    setAdVolume(volume: number) {\n      if (adVideoElement && adPlaying) {\n        const clamped = Math.max(0, Math.min(1, volume));\n        adVideoElement.volume = clamped;\n        adVideoElement.muted = clamped === 0;\n      }\n    },\n\n    getAdVolume(): number {\n      if (adVideoElement && adPlaying) {\n        return adVideoElement.volume;\n      }\n      return 1;\n    },\n    showPlaceholder() {\n      contentVideo.style.opacity = \"0\";\n      contentVideo.style.visibility = \"hidden\";\n      \n      if (!adContainerEl) {\n        const container = document.createElement(\"div\");\n        container.style.position = \"absolute\";\n        container.style.left = \"0\";\n        container.style.top = \"0\";\n        container.style.right = \"0\";\n        container.style.bottom = \"0\";\n        container.style.display = \"none\";\n        container.style.alignItems = \"center\";\n        container.style.justifyContent = \"center\";\n        container.style.pointerEvents = \"none\";\n        container.style.zIndex = \"10\";\n        container.style.backgroundColor = \"#000\";\n\n        contentVideo.parentElement?.appendChild(container);\n        adContainerEl = container;\n      }\n\n      if (adContainerEl) {\n        adContainerEl.style.display = \"flex\";\n        adContainerEl.style.pointerEvents = \"auto\";\n      }\n    },\n    hidePlaceholder() {\n      if (adContainerEl) {\n        adContainerEl.style.display = \"none\";\n        adContainerEl.style.pointerEvents = \"none\";\n      }\n      \n      if (!adPlaying) {\n        contentVideo.style.visibility = \"visible\";\n        contentVideo.style.opacity = \"1\";\n      }\n    },\n    getLoadedAdDuration() {\n      return currentAd?.duration;\n    },\n    getLoadedAdId() {\n      return currentAd?.id;\n    },\n    getPodAdCount() {\n      return podAds.length;\n    },\n    getPodTotalDurationMs() {\n      return podAds.reduce(\n        (total, ad) => total + (ad.duration > 0 ? ad.duration * 1000 : 0),\n        0\n      );\n    },\n  };\n}\n","const PRIVATE_HOST_PATTERNS: RegExp[] = [\n  /^localhost$/i,\n  /^127\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^0\\.0\\.0\\.0$/,\n  /^::1$/,\n  /^10\\.\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^192\\.168\\.\\d{1,3}\\.\\d{1,3}$/,\n  /^172\\.(1[6-9]|2\\d|3[0-1])\\.\\d{1,3}\\.\\d{1,3}$/,\n];\n\nexport function isLocalDevHost(hostname: string): boolean {\n  const host = hostname.replace(/^\\[/, \"\").replace(/\\]$/, \"\").toLowerCase();\n  if (!host) return false;\n  if (host.endsWith(\".local\") || host.endsWith(\".localhost\")) return true;\n  return PRIVATE_HOST_PATTERNS.some((pattern) => pattern.test(host));\n}\n\nexport function toDevSafeUrl(rawUrl: string | undefined): string {\n  if (!rawUrl) return rawUrl ?? \"\";\n\n  let url: URL;\n  try {\n    url = new URL(rawUrl);\n  } catch {\n    return rawUrl;\n  }\n\n  if (url.protocol !== \"http:\" && url.protocol !== \"https:\") {\n    return rawUrl;\n  }\n\n  if (!isLocalDevHost(url.hostname)) {\n    return rawUrl;\n  }\n\n  const cleanPath = url.pathname.replace(/\\/{2,}/g, \"/\") || \"/index.html\";\n  return `file://${cleanPath}`;\n}\n","import { toDevSafeUrl } from \"../utils/devUrl\";\n\ndeclare global {\n  interface Window {\n    goog?: any;\n  }\n}\n\nconst PAL_SDK_URL =\n  \"https://imasdk.googleapis.com/pal/sdkloader/pal.js\";\n\nlet _nonceLoader: any | undefined;\nlet _palLoadPromise: Promise<void> | undefined;\n\nfunction loadPalSdk(): Promise<void> {\n  if (typeof window !== \"undefined\" && window.goog?.pal) {\n    return Promise.resolve();\n  }\n\n  if (_palLoadPromise) return _palLoadPromise;\n\n  _palLoadPromise = new Promise<void>((resolve, reject) => {\n    const existing = document.querySelector(\n      'script[data-pal=\"true\"]'\n    ) as HTMLScriptElement | null;\n\n    if (existing) {\n      if (window.goog?.pal) {\n        resolve();\n        return;\n      }\n      const timeout = setTimeout(\n        () => reject(new Error(\"PAL SDK load timeout\")),\n        10000\n      );\n      existing.addEventListener(\"load\", () => {\n        clearTimeout(timeout);\n        resolve();\n      });\n      existing.addEventListener(\"error\", () => {\n        clearTimeout(timeout);\n        reject(new Error(\"PAL SDK load failed\"));\n      });\n      return;\n    }\n\n    const script = document.createElement(\"script\");\n    script.src = PAL_SDK_URL;\n    script.async = true;\n    script.setAttribute(\"data-pal\", \"true\");\n    script.onload = () => resolve();\n    script.onerror = () => reject(new Error(\"PAL SDK load failed\"));\n    document.head.appendChild(script);\n  });\n\n  return _palLoadPromise;\n}\n\nfunction getOrCreateNonceLoader(): any {\n  if (_nonceLoader) return _nonceLoader;\n  const goog = window.goog;\n  const consentSettings = new goog.pal.ConsentSettings();\n  consentSettings.allowStorage = true;\n  _nonceLoader = new goog.pal.NonceLoader(consentSettings);\n  return _nonceLoader;\n}\n\nexport interface PalNonceOptions {\n  videoWidth?: number;\n  videoHeight?: number;\n  descriptionUrl?: string;\n  ppid?: string;\n  sessionId?: string;\n  adWillAutoPlay?: boolean;\n  adWillPlayMuted?: boolean;\n  playerVolume?: number;\n  continuousPlayback?: boolean;\n}\n\nexport interface PalNonceManager {\n  generateNonce(options?: PalNonceOptions): Promise<string>;\n\n  getCurrentNonce(): string;\n\n  injectNonce(vastTagUrl: string): string;\n\n  sendPlaybackStart(): void;\n\n  sendPlaybackEnd(): void;\n\n  sendAdClick(): void;\n\n  sendAdTouch(event: MouseEvent | TouchEvent): void;\n\n  reset(): void;\n}\n\nexport function createPalNonceManager(): PalNonceManager {\n  let currentNonce = \"\";\n  let currentNonceManager: any | undefined;\n\n  return {\n    async generateNonce(options: PalNonceOptions = {}): Promise<string> {\n      try {\n        await loadPalSdk();\n\n        const loader = getOrCreateNonceLoader();\n        const goog = window.goog;\n\n        const request = new goog.pal.NonceRequest();\n        request.adWillAutoPlay = options.adWillAutoPlay ?? true;\n        request.adWillPlayMuted = options.adWillPlayMuted ?? false;\n        request.playerVolume =\n          options.playerVolume ?? (request.adWillPlayMuted ? 0 : 1);\n        request.continuousPlayback = options.continuousPlayback ?? true;\n        request.descriptionUrl = toDevSafeUrl(\n          options.descriptionUrl ||\n            (typeof window !== \"undefined\" ? window.location.href : \"\")\n        );\n        request.iconsSupported = true;\n        request.playerType = \"StormcloudVideoPlayer\";\n        request.playerVersion = \"1.0\";\n        request.supportedApiFrameworks = \"2,7,9\";\n        request.url = toDevSafeUrl(\n          options.descriptionUrl ||\n            (typeof window !== \"undefined\" ? window.location.href : \"\")\n        );\n        request.videoWidth = options.videoWidth || 640;\n        request.videoHeight = options.videoHeight || 480;\n\n        if (options.ppid) request.ppid = options.ppid;\n        if (options.sessionId) request.sessionId = options.sessionId;\n\n        console.log(\n          \"[PAL] NonceRequest before generateNonce:\",\n          JSON.stringify({\n            adWillAutoPlay: request.adWillAutoPlay,\n            adWillPlayMuted: request.adWillPlayMuted,\n            playerVolume: request.playerVolume,\n            continuousPlayback: request.continuousPlayback,\n            descriptionUrl: request.descriptionUrl,\n            iconsSupported: request.iconsSupported,\n            playerType: request.playerType,\n            playerVersion: request.playerVersion,\n            supportedApiFrameworks: request.supportedApiFrameworks,\n            url: request.url,\n            videoWidth: request.videoWidth,\n            videoHeight: request.videoHeight,\n            ppid: request.ppid,\n            sessionId: request.sessionId,\n          }, null, 2)\n        );\n\n        const manager = await loader.loadNonceManager(request);\n        currentNonceManager = manager;\n        currentNonce = manager.getNonce() as string;\n\n        console.log(\"[PAL] Nonce generated successfully\");\n        return currentNonce;\n      } catch (error) {\n        console.warn(\"[PAL] Failed to generate nonce:\", error);\n        currentNonce = \"\";\n        currentNonceManager = undefined;\n        return \"\";\n      }\n    },\n\n    getCurrentNonce(): string {\n      return currentNonce;\n    },\n\n    injectNonce(vastTagUrl: string): string {\n      if (!currentNonce || !vastTagUrl) return vastTagUrl;\n\n      try {\n        const url = new URL(vastTagUrl);\n        url.searchParams.delete(\"paln\");\n        url.searchParams.set(\"givn\", currentNonce);\n        return url.toString();\n      } catch {\n        let base = vastTagUrl\n          .replace(/([?&])paln=[^&]*/g, \"\")\n          .replace(/[?&]$/, \"\");\n        const sep = base.includes(\"?\") ? \"&\" : \"?\";\n        return `${base}${sep}givn=${encodeURIComponent(currentNonce)}`;\n      }\n    },\n\n    sendPlaybackStart(): void {\n      try {\n        currentNonceManager?.sendPlaybackStart();\n      } catch {}\n    },\n\n    sendPlaybackEnd(): void {\n      try {\n        currentNonceManager?.sendPlaybackEnd();\n      } catch {}\n    },\n\n    sendAdClick(): void {\n      try {\n        currentNonceManager?.sendAdClick();\n      } catch {}\n    },\n\n    sendAdTouch(event: MouseEvent | TouchEvent): void {\n      try {\n        currentNonceManager?.sendAdTouch(event);\n      } catch {}\n    },\n\n    reset(): void {\n      currentNonce = \"\";\n      currentNonceManager = undefined;\n    },\n  };\n}\n","import mqtt from \"mqtt\";\nimport type { MqttClient } from \"mqtt\";\nimport {\n  applyMQTTConfig,\n  buildMQTTBrokerUrl,\n  isMQTTEnabled,\n  mqttConfig,\n} from \"./mqttConfig\";\nimport type { MQTTConfig } from \"./mqttConfig\";\n\nconst LOG = \"[StormcloudVideoPlayer][MQTT]\";\n\nconst KEEPALIVE_SECONDS = 30;\nconst CONNECT_TIMEOUT_MS = 10_000;\n\nconst RECONNECT_BASE_MS = 5_000;\nconst RECONNECT_MAX_MS = 60_000;\nconst MAX_RECONNECT_ATTEMPTS = 8;\nconst COOLDOWN_MS = 10 * 60_000;\n\nexport type MQTTStatus = \"disconnected\" | \"connecting\" | \"connected\" | \"error\";\n\nlet client: MqttClient | null = null;\nlet status: MQTTStatus = \"disconnected\";\nlet reconnectAttempts = 0;\nlet reconnectTimer: ReturnType<typeof setTimeout> | null = null;\nlet stopped = false;\n\nexport function getMQTTStatus(): MQTTStatus {\n  return status;\n}\n\nexport function isMQTTConnected(): boolean {\n  return status === \"connected\" && client !== null && client.connected;\n}\n\nexport function isMQTTConfigured(): boolean {\n  return isMQTTEnabled();\n}\n\nexport function configureMQTT(overrides: Partial<MQTTConfig>): void {\n  applyMQTTConfig(overrides);\n  disconnectMQTT();\n}\n\nfunction clearReconnectTimer(): void {\n  if (reconnectTimer) {\n    clearTimeout(reconnectTimer);\n    reconnectTimer = null;\n  }\n}\n\nfunction teardownClient(): void {\n  if (client) {\n    try {\n      client.removeAllListeners();\n      client.end(true);\n    } catch {\n      // ignore teardown errors\n    }\n    client = null;\n  }\n}\n\nfunction scheduleReconnect(): void {\n  if (stopped || !isMQTTEnabled() || reconnectTimer) return;\n\n  if (reconnectAttempts >= MAX_RECONNECT_ATTEMPTS) {\n    console.warn(\n      `${LOG} giving up after ${reconnectAttempts} attempts; cooling down for ${\n        COOLDOWN_MS / 60_000\n      }m`\n    );\n    teardownClient();\n    status = \"disconnected\";\n    reconnectTimer = setTimeout(() => {\n      reconnectTimer = null;\n      reconnectAttempts = 0;\n      openConnection();\n    }, COOLDOWN_MS);\n    return;\n  }\n\n  const delay = Math.min(\n    RECONNECT_MAX_MS,\n    RECONNECT_BASE_MS * 2 ** reconnectAttempts\n  );\n  const jitter = Math.floor(Math.random() * 1_000);\n  reconnectAttempts += 1;\n\n  reconnectTimer = setTimeout(() => {\n    reconnectTimer = null;\n    openConnection();\n  }, delay + jitter);\n}\n\nfunction openConnection(): void {\n  if (stopped || !isMQTTEnabled()) return;\n\n  teardownClient();\n\n  const url = buildMQTTBrokerUrl();\n  status = \"connecting\";\n\n  const clientId = `stormcloud-vp-${Math.random().toString(36).slice(2, 9)}`;\n\n  try {\n    client = mqtt.connect(url, {\n      clientId,\n      username: mqttConfig.username,\n      password: mqttConfig.password,\n      keepalive: KEEPALIVE_SECONDS,\n      clean: true,\n      // Disable MQTT.js internal reconnect; we manage reconnection ourselves.\n      reconnectPeriod: 0,\n      connectTimeout: CONNECT_TIMEOUT_MS,\n      queueQoSZero: false,\n      reschedulePings: true,\n      // Root-cause fix for the Tizen 4.0 \"Keepalive timeout\" loop: MQTT.js's\n      // default timerVariant \"auto\" runs the keepalive interval inside a\n      // Blob-URL Web Worker (via worker-timers). On Samsung Tizen 4.0 (old\n      // WebKit) served from a file:// origin that worker can't tick reliably,\n      // so the keepalive counter trips onKeepaliveTimeout almost immediately\n      // after connect. Force the native setInterval timer instead; the main\n      // thread is free because video is decoded by the native AVPlay pipeline.\n      timerVariant: \"native\",\n    });\n  } catch (err) {\n    status = \"error\";\n    console.warn(`${LOG} connect() threw:`, err);\n    scheduleReconnect();\n    return;\n  }\n\n  client.on(\"connect\", () => {\n    status = \"connected\";\n    reconnectAttempts = 0;\n    clearReconnectTimer();\n    console.info(`${LOG} connected to ${url}`);\n  });\n\n  client.on(\"offline\", () => {\n    if (status === \"connected\") status = \"disconnected\";\n    console.warn(`${LOG} offline`);\n    scheduleReconnect();\n  });\n\n  client.on(\"error\", (err) => {\n    status = \"error\";\n    console.warn(`${LOG} error:`, err.message);\n    scheduleReconnect();\n  });\n\n  client.on(\"close\", () => {\n    if (status === \"connected\") status = \"disconnected\";\n    scheduleReconnect();\n  });\n}\n\nexport function initMQTTClient(): void {\n  if (client || !isMQTTEnabled()) return;\n  stopped = false;\n  reconnectAttempts = 0;\n  openConnection();\n}\n\nexport function ensureMQTTClient(): void {\n  if (isMQTTEnabled() && !client && !reconnectTimer) {\n    initMQTTClient();\n  }\n}\n\nexport function publishMQTT(\n  topic: string,\n  payload: Record<string, unknown>\n): boolean {\n  if (!isMQTTEnabled()) {\n    return false;\n  }\n\n  ensureMQTTClient();\n\n  if (!client || !client.connected) {\n    return false;\n  }\n\n  try {\n    client.publish(topic, JSON.stringify(payload), { qos: mqttConfig.qos });\n    return true;\n  } catch (err) {\n    console.warn(`${LOG} publish failed on ${topic}:`, err);\n    return false;\n  }\n}\n\nexport function disconnectMQTT(): void {\n  stopped = true;\n  clearReconnectTimer();\n  teardownClient();\n  reconnectAttempts = 0;\n  status = \"disconnected\";\n}\n","export const MQTT_CA_CERT_FILE = \"src/certs/emqxsl-ca.crt\";\n\nexport type MQTTConfig = {\n  enabled: boolean;\n  brokerAddress: string;\n  brokerPort: number;\n  wsPort: number;\n  username: string;\n  password: string;\n  topicPrefix: string;\n  qos: 0 | 1 | 2;\n  brokerUrl?: string;\n};\n\nexport const DEFAULT_MQTT_CONFIG: MQTTConfig = {\n  enabled: true,\n  brokerAddress: \"vecbae77.ala.us-east-1.emqxsl.com\",\n  brokerPort: 8883,\n  wsPort: 8084,\n  username: \"for-sonifi\",\n  password: \"sonifi-mqtt\",\n  topicPrefix: \"adstorm/players\",\n  qos: 1,\n};\n\nexport const mqttConfig: MQTTConfig = { ...DEFAULT_MQTT_CONFIG };\n\nexport function applyMQTTConfig(overrides: Partial<MQTTConfig>): void {\n  Object.assign(mqttConfig, overrides);\n}\n\nexport function isMQTTEnabled(): boolean {\n  return mqttConfig.enabled;\n}\n\nexport function buildMQTTBrokerUrl(): string {\n  if (mqttConfig.brokerUrl) return mqttConfig.brokerUrl;\n  return `wss://${mqttConfig.brokerAddress}:${mqttConfig.wsPort}/mqtt`;\n}\n\nexport function buildPlayerTopic(\n  licenseKey: string,\n  channel: \"metrics\" | \"impressions\" | \"heartbeat\"\n): string {\n  return `${mqttConfig.topicPrefix}/${licenseKey}/${channel}`;\n}\n","export interface VastEnvironmentSignals {\n  isCtv: boolean;\n  contentUrl?: string;\n  appId?: string;\n  appName?: string;\n  sessionId?: string;\n  deviceId?: string;\n  deviceIdType?: string;\n  limitAdTracking?: boolean;\n  deviceTypeHint?: number;\n}\n\nconst AIRY_ANDROID_APP_ID = \"com.freeairytv.android\";\nconst AIRY_WEBOS_APP_ID    = \"com.freeairytv.webos\";\nconst AIRY_TIZEN_APP_ID    = \"com.freeairytv.samsung\";\nconst AIRY_ROKU_APP_ID     = \"com.freeairytv.roku\";\nconst AIRY_APP_NAME = \"AiryTV Movies & TV\";\nconst AIRY_DEFAULT_CONTENT_URL = \"https://live.airy.tv\";\nconst CTV_SESSION_STORAGE_KEY = \"stormcloud.ctv.sid\";\nexport const PLAYER_ID_STORAGE_KEY = \"stormcloud.player.id\";\n\nconst LG_TEST_APP_ID      = \"com.hulu.plus\";\nconst LG_TEST_APP_NAME    = \"Hulu\";\nconst LG_TEST_CONTENT_URL = \"https://www.hulu.com/live-tv\";\n\nlet _lgTestDeviceId: string | undefined;\nfunction getLgTestDeviceId(): string {\n  if (!_lgTestDeviceId) _lgTestDeviceId = createUuid();\n  return _lgTestDeviceId;\n}\n\nfunction isLgWebOS(): boolean {\n  if (typeof navigator === \"undefined\") return false;\n  return /Web0S|webOS|LG Browser|LGSTB|LGE/i.test(navigator.userAgent);\n}\n\nfunction getDefaultAppId(): string {\n  if (typeof navigator === \"undefined\") return AIRY_ANDROID_APP_ID;\n  const ua = navigator.userAgent;\n  if (/Web0S|webOS|LG Browser|LGSTB|LGE/i.test(ua)) return AIRY_WEBOS_APP_ID;\n  if (/Tizen|Samsung/i.test(ua))                       return AIRY_TIZEN_APP_ID;\n  if (/Roku/i.test(ua))                                return AIRY_ROKU_APP_ID;\n  return AIRY_ANDROID_APP_ID;\n}\n\nconst DEVICE_ID_STORAGE_KEYS = [\n  \"rdid\",\n  \"ifa\",\n  \"advertisingId\",\n  \"advertising_id\",\n  \"deviceAdvertisingId\",\n  \"aaid\",\n  \"adid\",\n  \"rida\",\n  \"tifa\",\n  \"lgudid\",\n];\n\nconst ANDROID_ID_TYPES = new Set([\"aaid\", \"adid\"]);\n\nexport function resolveVastEnvironmentSignals(isCtv: boolean): VastEnvironmentSignals {\n  const bridgeSignals  = readNativeBridgeSignals();\n  const platformDevice = readPlatformNativeDeviceId();\n  const lg = isCtv && isLgWebOS();\n\n  const deviceId =\n    bridgeSignals.deviceId  ||\n    readStoredDeviceId()    ||\n    platformDevice.deviceId ||\n    (lg && platformDevice.limitAdTracking !== true ? getLgTestDeviceId() : undefined);\n  const deviceIdType =\n    bridgeSignals.deviceIdType  ||\n    readStoredString(\"deviceIdType\") ||\n    readStoredString(\"idtype\") ||\n    platformDevice.deviceIdType ||\n    inferDeviceIdType() ||\n    (lg ? \"lgudid\" : undefined);\n  const platformLat = bridgeSignals.deviceId\n    ? bridgeSignals.limitAdTracking\n    : platformDevice.limitAdTracking;\n  const limitAdTracking =\n    deviceId != null\n      ? platformLat ?? readStoredLimitAdTracking() ?? false\n      : undefined;\n\n  if (isCtv) {\n    return {\n      isCtv: true,\n      contentUrl:\n        bridgeSignals.contentUrl ||\n        readStoredString(\"contentUrl\") ||\n        (lg ? LG_TEST_CONTENT_URL : AIRY_DEFAULT_CONTENT_URL),\n      appId:\n        bridgeSignals.appId ||\n        readStoredString(\"appId\") ||\n        readStoredString(\"msid\") ||\n        (lg ? LG_TEST_APP_ID : getDefaultAppId()),\n      appName:\n        bridgeSignals.appName ||\n        readStoredString(\"appName\") ||\n        readStoredString(\"an\") ||\n        (lg ? LG_TEST_APP_NAME : AIRY_APP_NAME),\n      sessionId: getOrCreateCtvSessionId(),\n      ...(deviceId ? { deviceId } : {}),\n      ...(deviceIdType ? { deviceIdType } : {}),\n      ...(limitAdTracking != null ? { limitAdTracking } : {}),\n      deviceTypeHint: 5,\n    };\n  }\n\n  return {\n    isCtv: false,\n    ...(deviceId ? { deviceId } : {}),\n    ...(deviceIdType ? { deviceIdType } : {}),\n    ...(limitAdTracking != null ? { limitAdTracking } : {}),\n  };\n}\n\nexport function inferDeviceIdType(): string | undefined {\n  if (typeof navigator === \"undefined\") {\n    return undefined;\n  }\n\n  const ua = navigator.userAgent;\n  if (/Roku/i.test(ua)) return \"rida\";\n  if (/Tizen|Samsung/i.test(ua)) return \"tifa\";\n  if (/AppleTV|Apple TV/i.test(ua)) return \"tvOS\";\n  if (/AFT|Fire TV|Amazon/i.test(ua)) return \"afai\";\n  if (/Web0S|webOS|LG Browser|LGSTB|LGE/i.test(ua)) return \"lgudid\";\n  if (/Android|Google TV/i.test(ua)) return \"aaid\";\n  if (/iPhone|iPad|iPod/i.test(ua)) return \"idfa\";\n  return undefined;\n}\n\nexport function isEquivalentDeviceIdType(\n  tagType: string | undefined,\n  runtimeType: string | undefined\n): boolean {\n  if (!tagType || !runtimeType) return false;\n  const tag = tagType.toLowerCase();\n  const runtime = runtimeType.toLowerCase();\n  if (tag === runtime) return true;\n  return ANDROID_ID_TYPES.has(tag) && ANDROID_ID_TYPES.has(runtime);\n}\n\nexport function resolveNativeDeviceId(): string | undefined {\n  const bridgeSignals = readNativeBridgeSignals();\n  const platformDevice = readPlatformNativeDeviceId();\n  const deviceId =\n    bridgeSignals.deviceId ||\n    readStoredDeviceId() ||\n    platformDevice.deviceId;\n\n  if (!deviceId || isMacroPlaceholder(deviceId) || isZeroedAdId(deviceId)) {\n    return undefined;\n  }\n\n  return deviceId;\n}\n\nexport function getOrCreateStoredUuid(storageKey: string): string | undefined {\n  if (typeof window === \"undefined\") {\n    return undefined;\n  }\n\n  const existing = readPersistentId(storageKey);\n  if (existing) {\n    writePersistentId(storageKey, existing);\n    return existing;\n  }\n\n  const id = createUuid();\n  writePersistentId(storageKey, id);\n  return id;\n}\n\nfunction getOrCreateCtvSessionId(): string {\n  const existing = readPersistentId(CTV_SESSION_STORAGE_KEY);\n  if (existing) {\n    writePersistentId(CTV_SESSION_STORAGE_KEY, existing);\n    return existing;\n  }\n\n  const sessionId = createUuid();\n  writePersistentId(CTV_SESSION_STORAGE_KEY, sessionId);\n  return sessionId;\n}\n\nfunction readPersistentId(storageKey: string): string | undefined {\n  return readStoredString(storageKey) || readCookie(storageKey);\n}\n\nfunction writePersistentId(storageKey: string, value: string): void {\n  try {\n    window.localStorage?.setItem(storageKey, value);\n  } catch {}\n  writeCookie(storageKey, value);\n}\n\nconst PERSISTENT_ID_COOKIE_MAX_AGE = 60 * 60 * 24 * 365 * 5; // ~5 years\n\nfunction readCookie(name: string): string | undefined {\n  if (typeof document === \"undefined\") {\n    return undefined;\n  }\n\n  try {\n    const prefix = encodeURIComponent(name) + \"=\";\n    const parts = document.cookie ? document.cookie.split(\";\") : [];\n    for (const part of parts) {\n      const entry = part.trim();\n      if (entry.startsWith(prefix)) {\n        return decodeURIComponent(entry.slice(prefix.length)) || undefined;\n      }\n    }\n  } catch {}\n\n  return undefined;\n}\n\nfunction writeCookie(name: string, value: string): void {\n  if (typeof document === \"undefined\") {\n    return;\n  }\n\n  try {\n    document.cookie =\n      encodeURIComponent(name) +\n      \"=\" +\n      encodeURIComponent(value) +\n      \";path=/;max-age=\" +\n      PERSISTENT_ID_COOKIE_MAX_AGE +\n      \";SameSite=Lax\";\n  } catch {}\n}\n\nfunction createUuid(): string {\n  if (typeof crypto !== \"undefined\" && typeof crypto.randomUUID === \"function\") {\n    return crypto.randomUUID();\n  }\n\n  const bytes = new Uint8Array(16);\n  if (typeof crypto !== \"undefined\" && typeof crypto.getRandomValues === \"function\") {\n    crypto.getRandomValues(bytes);\n  } else {\n    let seed = Date.now() ^ Math.floor(performanceNow() * 1e3);\n    for (let i = 0; i < 16; i++) {\n      seed = (seed * 1103515245 + 12345) & 0x7fffffff;\n      bytes[i] = (seed ^ Math.floor(Math.random() * 256)) & 0xff;\n    }\n  }\n\n  bytes[6] = ((bytes[6] ?? 0) & 0x0f) | 0x40;\n  bytes[8] = ((bytes[8] ?? 0) & 0x3f) | 0x80;\n\n  let hex = \"\";\n  for (let i = 0; i < 16; i++) {\n    hex += (bytes[i] ?? 0).toString(16).padStart(2, \"0\");\n  }\n\n  return (\n    hex.slice(0, 8) +\n    \"-\" +\n    hex.slice(8, 12) +\n    \"-\" +\n    hex.slice(12, 16) +\n    \"-\" +\n    hex.slice(16, 20) +\n    \"-\" +\n    hex.slice(20, 32)\n  );\n}\n\nfunction performanceNow(): number {\n  try {\n    if (typeof performance !== \"undefined\" && typeof performance.now === \"function\") {\n      return performance.now();\n    }\n  } catch {}\n  return 0;\n}\n\nfunction readPlatformNativeDeviceId(): {\n  deviceId?: string;\n  deviceIdType?: string;\n  limitAdTracking?: boolean;\n} {\n  if (typeof window === \"undefined\") return {};\n\n  try {\n    const adinfo = (window as any).webapis?.adinfo;\n    if (adinfo) {\n      const tifa: unknown =\n        typeof adinfo.getTIFA === \"function\" ? adinfo.getTIFA() : adinfo.tifa;\n      if (typeof tifa === \"string\" && tifa && !isMacroPlaceholder(tifa)) {\n        const lat: unknown =\n          typeof adinfo.isLATEnabled === \"function\"\n            ? adinfo.isLATEnabled()\n            : undefined;\n        return {\n          deviceId: tifa,\n          deviceIdType: \"tifa\",\n          ...(typeof lat === \"boolean\" ? { limitAdTracking: lat } : {}),\n        };\n      }\n    }\n  } catch {}\n\n  try {\n    const webOSDev = (window as any).webOSDev;\n    if (webOSDev) {\n      const lgudid: unknown =\n        typeof webOSDev.LGUDID === \"function\"\n          ? webOSDev.LGUDID()\n          : webOSDev.lgudid ?? webOSDev.LGUDID;\n      if (typeof lgudid === \"string\" && lgudid) {\n        if (isZeroedAdId(lgudid)) {\n          return { deviceIdType: \"lgudid\", limitAdTracking: true };\n        }\n        if (!isMacroPlaceholder(lgudid)) {\n          return { deviceId: lgudid, deviceIdType: \"lgudid\", limitAdTracking: false };\n        }\n      }\n    }\n  } catch {}\n\n  try {\n    const roku = (window as any).Roku;\n    if (roku) {\n      const rida: unknown =\n        typeof roku.getPublisherUniqueId === \"function\"\n          ? roku.getPublisherUniqueId()\n          : roku.rida;\n      if (typeof rida === \"string\" && rida && !isMacroPlaceholder(rida)) {\n        return { deviceId: rida, deviceIdType: \"rida\", limitAdTracking: false };\n      }\n    }\n  } catch {}\n\n  return {};\n}\n\nconst ZEROED_AD_ID_PATTERNS: ReadonlySet<string> = new Set([\n  \"38400000-8cf0-11bd-b23e-10b96e40000d\",\n  \"00000000-0000-0000-0000-000000000000\",\n]);\n\nfunction isMacroPlaceholder(value: string): boolean {\n  const t = value.trim();\n  return !t ||\n    /^(\\[[^\\]]*\\]|\\{[^}]*\\}|%%[^%]*%%)$/.test(t) ||\n    /^(unknown|null|undefined|none|n\\/a|\\$\\{[^}]+\\})$/i.test(t) ||\n    ZEROED_AD_ID_PATTERNS.has(t.toLowerCase());\n}\n\nfunction isZeroedAdId(value: string): boolean {\n  return ZEROED_AD_ID_PATTERNS.has(value.trim().toLowerCase());\n}\n\nfunction readNativeBridgeSignals(): {\n  contentUrl?: string;\n  appId?: string;\n  appName?: string;\n  deviceId?: string;\n  deviceIdType?: string;\n  limitAdTracking?: boolean;\n} {\n  if (typeof window === \"undefined\") {\n    return {};\n  }\n\n  const candidates = [\n    (window as any).__STORMCLOUD_CTV_AD_INFO__,\n    (window as any).__STORMCLOUD_CTV__,\n    (window as any).stormcloudCtv,\n    (window as any).AiryTV,\n    (window as any).Android,\n    (window as any).webOS,\n    (window as any).tizen,\n    (window as any).amazon,\n  ].filter(Boolean);\n\n  for (const source of candidates) {\n    const contentUrl =\n      readBridgeValue(source, [\"contentUrl\", \"url\", \"videoUrl\", \"canonicalUrl\"]) ||\n      undefined;\n    const appId =\n      readBridgeValue(source, [\"appId\", \"msid\", \"applicationId\", \"packageName\"]) ||\n      undefined;\n    const appName =\n      readBridgeValue(source, [\"appName\", \"an\", \"applicationName\"]) || undefined;\n    const deviceId =\n      readBridgeValue(source, [\n        \"rdid\",\n        \"ifa\",\n        \"advertisingId\",\n        \"adId\",\n        \"deviceId\",\n        \"lgudid\",\n        \"LGUDID\",\n        \"tifa\",\n        \"rida\",\n        \"afai\",\n        \"aaid\",\n      ]) || undefined;\n\n    if (!contentUrl && !deviceId && !appId && !appName) continue;\n\n    const deviceIdType =\n      readBridgeValue(source, [\n        \"idtype\",\n        \"deviceIdType\",\n        \"advertisingIdType\",\n        \"idType\",\n      ]) || inferDeviceIdType();\n    const limitAdTracking = readBridgeBoolean(source, [\n      \"is_lat\",\n      \"limitAdTracking\",\n      \"limitedAdTracking\",\n      \"lat\",\n    ]);\n\n    return {\n      ...(contentUrl ? { contentUrl } : {}),\n      ...(appId ? { appId } : {}),\n      ...(appName ? { appName } : {}),\n      ...(deviceId ? { deviceId } : {}),\n      ...(deviceId && deviceIdType ? { deviceIdType } : {}),\n      ...(deviceId && limitAdTracking != null ? { limitAdTracking } : {}),\n    };\n  }\n\n  return {};\n}\n\nfunction readBridgeValue(source: any, keys: string[]): string | undefined {\n  for (const key of keys) {\n    const value = source?.[key];\n    if (typeof value === \"string\" && value) {\n      return value;\n    }\n    if (typeof value === \"function\") {\n      try {\n        const result = value.call(source);\n        if (typeof result === \"string\" && result) {\n          return result;\n        }\n      } catch {}\n    }\n  }\n  return undefined;\n}\n\nfunction readBridgeBoolean(source: any, keys: string[]): boolean | undefined {\n  for (const key of keys) {\n    const value = source?.[key];\n    const normalized = normalizeBoolean(value);\n    if (normalized != null) {\n      return normalized;\n    }\n    if (typeof value === \"function\") {\n      try {\n        const result = normalizeBoolean(value.call(source));\n        if (result != null) {\n          return result;\n        }\n      } catch {}\n    }\n  }\n  return undefined;\n}\n\nfunction readStoredDeviceId(): string | undefined {\n  for (const key of DEVICE_ID_STORAGE_KEYS) {\n    const value = readStoredString(key);\n    if (value) {\n      return value;\n    }\n  }\n  return undefined;\n}\n\nfunction readStoredString(key: string): string | undefined {\n  if (typeof window === \"undefined\") {\n    return undefined;\n  }\n\n  try {\n    const value = window.localStorage?.getItem(key);\n    return value || undefined;\n  } catch {\n    return undefined;\n  }\n}\n\nfunction readStoredLimitAdTracking(): boolean | undefined {\n  return normalizeBoolean(\n    readStoredString(\"limitAdTracking\") ||\n      readStoredString(\"limitedAdTracking\") ||\n      readStoredString(\"is_lat\")\n  );\n}\n\nfunction normalizeBoolean(value: unknown): boolean | undefined {\n  if (typeof value === \"boolean\") {\n    return value;\n  }\n  if (typeof value === \"number\") {\n    return value === 1;\n  }\n  if (typeof value === \"string\") {\n    const normalized = value.toLowerCase();\n    if (normalized === \"1\" || normalized === \"true\" || normalized === \"yes\") {\n      return true;\n    }\n    if (normalized === \"0\" || normalized === \"false\" || normalized === \"no\") {\n      return false;\n    }\n  }\n  return undefined;\n}\n","import type {\n  ClientInfo,\n  AdDetectInfo,\n  AdLoadedInfo,\n  AdImpressionInfo,\n  PlayerAnalyticsContext,\n  StormcloudVideoPlayerConfig,\n} from \"../types\";\n\nimport { buildPlayerTopic, isMQTTEnabled } from \"./mqttConfig\";\nimport { ensureMQTTClient, publishMQTT } from \"./mqttClient\";\nimport {\n  getOrCreateStoredUuid,\n  PLAYER_ID_STORAGE_KEY,\n  resolveNativeDeviceId,\n} from \"./vastEnvironmentSignals\";\n\nlet cachedBrowserId: string | null = null;\n\nexport function buildAnalyticsContext(\n  config: Pick<StormcloudVideoPlayerConfig, \"debugAdTiming\" | \"isLiveStream\">\n): PlayerAnalyticsContext {\n  const context: PlayerAnalyticsContext = {};\n  if (config.debugAdTiming) {\n    context.debugAdTiming = true;\n  }\n  if (config.isLiveStream !== undefined) {\n    context.inputStreamType = config.isLiveStream ? \"live\" : \"vod\";\n  }\n  return context;\n}\n\nexport function getClientInfo(): ClientInfo {\n  const ua = navigator.userAgent;\n  const platform = navigator.platform;\n  const vendor = navigator.vendor || \"\";\n  const maxTouchPoints = navigator.maxTouchPoints || 0;\n  const memory = (navigator as any).deviceMemory || null;\n  const hardwareConcurrency = navigator.hardwareConcurrency || 1;\n\n  const screenInfo = {\n    width: screen?.width,\n    height: screen?.height,\n    availWidth: screen?.availWidth,\n    availHeight: screen?.availHeight,\n    orientation: (screen?.orientation as any)?.type || \"\",\n    pixelDepth: screen?.pixelDepth,\n  };\n\n  let deviceType: \"tv\" | \"mobile\" | \"tablet\" | \"desktop\" = \"desktop\";\n  let brand = \"Unknown\";\n  let os = \"Unknown\";\n  let model = \"\";\n  let isSmartTV = false;\n  let isAndroid = false;\n  let isWebView = false;\n  let isWebApp = false;\n\n  if (ua.includes(\"Web0S\")) {\n    brand = \"LG\";\n    os = \"webOS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n    const webosMatch = ua.match(/Web0S\\/([^\\s]+)/);\n    model = webosMatch ? `webOS ${webosMatch[1]}` : \"webOS TV\";\n  } else if (ua.includes(\"Tizen\")) {\n    brand = \"Samsung\";\n    os = \"Tizen\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n    const tizenMatch = ua.match(/Tizen\\/([^\\s]+)/);\n    const tvMatch = ua.match(/(?:Smart-TV|SMART-TV|TV)/i) ? \"Smart TV\" : \"\";\n    model = tizenMatch\n      ? `Tizen ${tizenMatch[1]} ${tvMatch}`.trim()\n      : \"Tizen TV\";\n  } else if (ua.includes(\"Philips\")) {\n    brand = \"Philips\";\n    os = \"Saphi\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"Sharp\") || ua.includes(\"AQUOS\")) {\n    brand = \"Sharp\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (\n    ua.includes(\"Android\") &&\n    (ua.includes(\"Sony\") || vendor.includes(\"Sony\"))\n  ) {\n    brand = \"Sony\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (\n    ua.includes(\"Android\") &&\n    (ua.includes(\"NetCast\") || ua.includes(\"LG\"))\n  ) {\n    brand = \"LG\";\n    os = \"Android TV\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\" Roku\") || ua.includes(\"Roku/\")) {\n    brand = \"Roku\";\n    os = \"Roku OS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  } else if (ua.includes(\"AppleTV\")) {\n    brand = \"Apple\";\n    os = \"tvOS\";\n    isSmartTV = true;\n    deviceType = \"tv\";\n  }\n\n  if (ua.includes(\"Android\")) {\n    isAndroid = true;\n    os = \"Android\";\n    deviceType = /Mobile/.test(ua) ? \"mobile\" : \"tablet\";\n\n    if (\n      ua.includes(\"Android\") &&\n      (maxTouchPoints === 0 ||\n        ua.includes(\"Google TV\") ||\n        ua.includes(\"XiaoMi\"))\n    ) {\n      deviceType = \"tv\";\n      isSmartTV = true;\n      brand = brand === \"Unknown\" ? \"Android TV\" : brand;\n    }\n\n    const androidModelMatch = ua.match(/\\(([^)]*Android[^)]*)\\)/);\n    if (androidModelMatch && androidModelMatch[1]) {\n      model = androidModelMatch[1];\n    }\n  }\n\n  if (/iPad|iPhone|iPod/.test(ua)) {\n    os = \"iOS\";\n    deviceType = \"mobile\";\n    brand = \"Apple\";\n    if (navigator.maxTouchPoints > 1 && /iPad/.test(ua)) {\n      deviceType = \"tablet\";\n    }\n  }\n\n  if (!isAndroid && !isSmartTV && !/Mobile/.test(ua)) {\n    if (ua.includes(\"Windows\")) {\n      os = \"Windows\";\n      deviceType = \"desktop\";\n    } else if (ua.includes(\"Mac\") && !/iPhone/.test(ua)) {\n      os = \"macOS\";\n      deviceType = \"desktop\";\n      if (maxTouchPoints > 1) deviceType = \"tablet\";\n    } else if (ua.includes(\"Linux\")) {\n      os = \"Linux\";\n      deviceType = \"desktop\";\n    }\n  }\n\n  if (brand === \"Unknown\") {\n    if (vendor.includes(\"Google\") || ua.includes(\"Chrome\")) brand = \"Google\";\n    if (vendor.includes(\"Apple\")) brand = \"Apple\";\n    if (vendor.includes(\"Samsung\") || ua.includes(\"SM-\")) brand = \"Samsung\";\n  }\n\n  isWebView = /wv|WebView|Linux; U;/.test(ua);\n\n  if (window?.outerHeight === 0 && window?.outerWidth === 0) {\n    isWebView = true;\n  }\n\n  isWebApp =\n    window.matchMedia(\"(display-mode: standalone)\").matches ||\n    (window.navigator as any).standalone === true ||\n    window.screen?.orientation?.angle !== undefined;\n\n  return {\n    brand,\n    os,\n    model: model || ua.substring(0, 50) + \"...\",\n    deviceType,\n    isSmartTV,\n    isAndroid,\n    isWebView,\n    isWebApp,\n    domain: window.location.hostname,\n    origin: window.location.origin,\n    path: window.location.pathname,\n    userAgent: ua,\n    vendor,\n    platform,\n    screen: screenInfo,\n    hardwareConcurrency,\n    deviceMemory: memory,\n    maxTouchPoints,\n    language: navigator.language,\n    languages: navigator.languages?.join(\",\") || \"\",\n    cookieEnabled: navigator.cookieEnabled,\n    doNotTrack: navigator.doNotTrack || \"\",\n    referrer: document.referrer,\n    visibilityState: document.visibilityState,\n  };\n}\n\nasync function sha256Hex(input: string): Promise<string> {\n  if (typeof crypto !== \"undefined\" && crypto.subtle?.digest) {\n    try {\n      await crypto.subtle.digest(\"SHA-256\", new Uint8Array([1, 2, 3]));\n\n      let encodedData: BufferSource;\n      if (typeof TextEncoder !== \"undefined\") {\n        encodedData = new TextEncoder().encode(input);\n      } else {\n        const utf8 = unescape(encodeURIComponent(input));\n        const buffer = new Uint8Array(utf8.length);\n        for (let i = 0; i < utf8.length; i++) {\n          buffer[i] = utf8.charCodeAt(i);\n        }\n        encodedData = buffer;\n      }\n\n      const hashBuffer = await crypto.subtle.digest(\"SHA-256\", encodedData);\n      return Array.from(new Uint8Array(hashBuffer))\n        .map((b) => b.toString(16).padStart(2, \"0\"))\n        .join(\"\");\n    } catch {\n      console.warn(\n        \"[StormcloudVideoPlayer] crypto.subtle not supported, using fallback hash\"\n      );\n    }\n  }\n\n  let hash = 0;\n  for (let i = 0; i < input.length; i++) {\n    const char = input.charCodeAt(i);\n    hash = (hash << 5) - hash + char;\n    hash = hash & hash;\n  }\n\n  const fallbackHash = Math.abs(hash).toString(16).padStart(8, \"0\");\n  const timestamp = Date.now().toString(16).padStart(12, \"0\");\n  const random = Math.random().toString(16).substring(2, 14).padStart(12, \"0\");\n\n  return (fallbackHash + timestamp + random).padEnd(64, \"0\");\n}\n\nfunction resolvePlayerIdentitySeed(clientInfo: ClientInfo): string {\n  const nativeDeviceId = resolveNativeDeviceId();\n  if (nativeDeviceId) {\n    return `device:${nativeDeviceId}`;\n  }\n\n  const persistedId = getOrCreateStoredUuid(PLAYER_ID_STORAGE_KEY);\n  if (persistedId) {\n    return `persisted:${persistedId}`;\n  }\n\n  return `fingerprint:${JSON.stringify(clientInfo)}`;\n}\n\nexport async function getBrowserID(clientInfo: ClientInfo): Promise<string> {\n  if (cachedBrowserId) {\n    return cachedBrowserId;\n  }\n\n  cachedBrowserId = await sha256Hex(resolvePlayerIdentitySeed(clientInfo));\n  return cachedBrowserId;\n}\n\ntype PlayerMetricFlags = {\n  adLoaded?: boolean;\n  adDetect?: boolean;\n  captureAt?: string;\n};\n\nfunction canPublish(licenseKey: string | undefined): licenseKey is string {\n  return Boolean(isMQTTEnabled() && licenseKey);\n}\n\nasync function buildPlayerMetricEvent(\n  context: PlayerAnalyticsContext = {},\n  flags: PlayerMetricFlags = {}\n): Promise<Record<string, unknown>> {\n  const clientInfo = getClientInfo();\n\n  const debugAdTiming = !!context.debugAdTiming;\n  if (debugAdTiming) {\n    console.log(\"[StormcloudVideoPlayer] clientInfo: \", JSON.stringify(clientInfo, null, 2));\n  }\n\n  const playerId = await getBrowserID(clientInfo);\n\n  if (debugAdTiming) {\n    console.log(\"[StormcloudVideoPlayer] playerId: \", playerId);\n  }\n\n  const captureAt = flags.captureAt ?? new Date().toISOString();\n\n  return {\n    player_id: playerId,\n    device_type: clientInfo.deviceType,\n    os: clientInfo.os.toLowerCase(),\n    ad_loaded: flags.adLoaded ?? false,\n    ad_detect: flags.adDetect ?? false,\n    capture_at: captureAt,\n    ...(context.inputStreamType\n      ? { input_stream_type: context.inputStreamType }\n      : {}),\n  };\n}\n\nfunction publishTracking(\n  licenseKey: string,\n  channel: \"metrics\" | \"impressions\" | \"heartbeat\",\n  body: Record<string, unknown>\n): void {\n  ensureMQTTClient();\n  publishMQTT(buildPlayerTopic(licenseKey, channel), body);\n}\n\nexport async function sendInitialTracking(\n  licenseKey?: string,\n  context: PlayerAnalyticsContext = {}\n): Promise<void> {\n  if (!canPublish(licenseKey)) return;\n\n  try {\n    const metricEvent = await buildPlayerMetricEvent(context, {\n      adLoaded: false,\n      adDetect: false,\n    });\n\n    publishTracking(licenseKey, \"metrics\", {\n      events: [metricEvent],\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending initial tracking data:\",\n      error\n    );\n  }\n}\n\nexport async function sendAdDetectTracking(\n  licenseKey: string | undefined,\n  adDetectInfo: AdDetectInfo,\n  context: PlayerAnalyticsContext = {}\n): Promise<void> {\n  try {\n    await sendHeartbeat(licenseKey, context, {\n      adDetect: true,\n      captureAt: adDetectInfo.timestamp,\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad detect tracking:\",\n      error\n    );\n  }\n}\n\nexport async function sendAdLoadedTracking(\n  licenseKey: string | undefined,\n  adLoadedInfo: AdLoadedInfo,\n  context: PlayerAnalyticsContext = {}\n): Promise<void> {\n  try {\n    await sendHeartbeat(licenseKey, context, {\n      adLoaded: true,\n      captureAt: adLoadedInfo.timestamp,\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad loaded tracking:\",\n      error\n    );\n  }\n}\n\nexport async function sendAdImpressionTracking(\n  licenseKey: string | undefined,\n  adImpressionInfo: AdImpressionInfo,\n  context: PlayerAnalyticsContext = {}\n): Promise<void> {\n  if (!canPublish(licenseKey)) return;\n\n  try {\n    const metricEvent = await buildPlayerMetricEvent(context, {\n      captureAt: adImpressionInfo.timestamp,\n    });\n\n    publishTracking(licenseKey, \"heartbeat\", metricEvent);\n    publishTracking(licenseKey, \"impressions\", {\n      events: [\n        {\n          player_id: metricEvent.player_id,\n          ad_played_count: 1,\n          ad_url: adImpressionInfo.adUrl,\n          capture_at: adImpressionInfo.timestamp,\n        },\n      ],\n    });\n  } catch (error) {\n    console.error(\n      \"[StormcloudVideoPlayer] Error sending ad impression tracking:\",\n      error\n    );\n  }\n}\n\nexport async function sendHeartbeat(\n  licenseKey?: string,\n  context: PlayerAnalyticsContext = {},\n  flags: PlayerMetricFlags = {}\n): Promise<void> {\n  if (!canPublish(licenseKey)) return;\n\n  try {\n    const heartbeatData = await buildPlayerMetricEvent(context, flags);\n    publishTracking(licenseKey, \"heartbeat\", heartbeatData);\n  } catch (error) {\n    console.error(\"[StormcloudVideoPlayer] Error sending heartbeat:\", error);\n  }\n}\n","export function polyfillURLSearchParams(): void {\n  if (typeof URLSearchParams !== 'undefined') {\n    return;\n  }\n\n  class URLSearchParamsPolyfill {\n    private params: Map<string, string[]>;\n\n    constructor(init?: string | URLSearchParamsPolyfill) {\n      this.params = new Map();\n\n      if (typeof init === 'string') {\n        this.parseQueryString(init);\n      } else if (init instanceof URLSearchParamsPolyfill) {\n        init.forEach((value, key) => {\n          this.append(key, value);\n        });\n      }\n    }\n\n    private parseQueryString(query: string): void {\n      const cleanQuery = query.startsWith('?') ? query.slice(1) : query;\n      if (!cleanQuery) return;\n\n      cleanQuery.split('&').forEach((param) => {\n        const [key, value] = param.split('=');\n        if (key) {\n          const decodedKey = this.safeDecodeURIComponent(key);\n          const decodedValue = value ? this.safeDecodeURIComponent(value) : '';\n          this.append(decodedKey, decodedValue);\n        }\n      });\n    }\n\n    private safeDecodeURIComponent(str: string): string {\n      try {\n        return decodeURIComponent(str.replace(/\\+/g, ' '));\n      } catch (e) {\n        return str;\n      }\n    }\n\n    append(name: string, value: string): void {\n      const values = this.params.get(name) || [];\n      values.push(String(value));\n      this.params.set(name, values);\n    }\n\n    delete(name: string): void {\n      this.params.delete(name);\n    }\n\n    get(name: string): string | null {\n      const values = this.params.get(name);\n      return values && values.length > 0 && values[0] !== undefined ? values[0] : null;\n    }\n\n    getAll(name: string): string[] {\n      return this.params.get(name) || [];\n    }\n\n    has(name: string): boolean {\n      return this.params.has(name);\n    }\n\n    set(name: string, value: string): void {\n      this.params.set(name, [String(value)]);\n    }\n\n    forEach(callback: (value: string, key: string, parent: URLSearchParamsPolyfill) => void): void {\n      this.params.forEach((values, key) => {\n        values.forEach((value) => {\n          callback(value, key, this);\n        });\n      });\n    }\n\n    toString(): string {\n      const parts: string[] = [];\n      this.params.forEach((values, key) => {\n        values.forEach((value) => {\n          parts.push(`${encodeURIComponent(key)}=${encodeURIComponent(value)}`);\n        });\n      });\n      return parts.join('&');\n    }\n  }\n\n  // @ts-ignore\n  window.URLSearchParams = URLSearchParamsPolyfill;\n}\n\nexport function polyfillTextEncoder(): void {\n  if (typeof TextEncoder !== 'undefined') {\n    return;\n  }\n\n  class TextEncoderPolyfill {\n    encoding = 'utf-8';\n\n    encode(str: string): Uint8Array {\n      const utf8: number[] = [];\n      for (let i = 0; i < str.length; i++) {\n        let charcode = str.charCodeAt(i);\n        if (charcode < 0x80) {\n          utf8.push(charcode);\n        } else if (charcode < 0x800) {\n          utf8.push(0xc0 | (charcode >> 6), 0x80 | (charcode & 0x3f));\n        } else if (charcode < 0xd800 || charcode >= 0xe000) {\n          utf8.push(\n            0xe0 | (charcode >> 12),\n            0x80 | ((charcode >> 6) & 0x3f),\n            0x80 | (charcode & 0x3f)\n          );\n        } else {\n          i++;\n          charcode = 0x10000 + (((charcode & 0x3ff) << 10) | (str.charCodeAt(i) & 0x3ff));\n          utf8.push(\n            0xf0 | (charcode >> 18),\n            0x80 | ((charcode >> 12) & 0x3f),\n            0x80 | ((charcode >> 6) & 0x3f),\n            0x80 | (charcode & 0x3f)\n          );\n        }\n      }\n      return new Uint8Array(utf8);\n    }\n  }\n\n  // @ts-ignore\n  window.TextEncoder = TextEncoderPolyfill;\n}\n\nexport function polyfillPromiseFinally(): void {\n  if (typeof Promise !== 'undefined' && !Promise.prototype.finally) {\n    Promise.prototype.finally = function (callback: () => void) {\n      const constructor = this.constructor as PromiseConstructor;\n      return this.then(\n        (value) => constructor.resolve(callback()).then(() => value),\n        (reason) =>\n          constructor.resolve(callback()).then(() => {\n            throw reason;\n          })\n      );\n    };\n  }\n}\n\nexport function polyfillObjectAssign(): void {\n  if (typeof Object.assign !== 'function') {\n    Object.assign = function (target: any, ...sources: any[]) {\n      if (target == null) {\n        throw new TypeError('Cannot convert undefined or null to object');\n      }\n\n      const to = Object(target);\n\n      for (let i = 0; i < sources.length; i++) {\n        const nextSource = sources[i];\n\n        if (nextSource != null) {\n          for (const nextKey in nextSource) {\n            if (Object.prototype.hasOwnProperty.call(nextSource, nextKey)) {\n              to[nextKey] = nextSource[nextKey];\n            }\n          }\n        }\n      }\n\n      return to;\n    };\n  }\n}\n\nexport function polyfillArrayFrom(): void {\n  if (!Array.from) {\n    Array.from = function (arrayLike: any, mapFn?: any, thisArg?: any) {\n      const items = Object(arrayLike);\n      if (arrayLike == null) {\n        throw new TypeError('Array.from requires an array-like object');\n      }\n\n      const len = items.length >>> 0;\n      const result = new Array(len);\n\n      for (let i = 0; i < len; i++) {\n        if (mapFn) {\n          result[i] = mapFn.call(thisArg, items[i], i);\n        } else {\n          result[i] = items[i];\n        }\n      }\n\n      return result;\n    };\n  }\n}\n\nexport function polyfillStringStartsWith(): void {\n  if (!String.prototype.startsWith) {\n    String.prototype.startsWith = function (search: string, pos?: number) {\n      pos = !pos || pos < 0 ? 0 : +pos;\n      return this.substring(pos, pos + search.length) === search;\n    };\n  }\n}\n\nexport function polyfillStringEndsWith(): void {\n  if (!String.prototype.endsWith) {\n    String.prototype.endsWith = function (search: string, length?: number) {\n      if (length === undefined || length > this.length) {\n        length = this.length;\n      }\n      return this.substring(length - search.length, length) === search;\n    };\n  }\n}\n\nexport function polyfillStringIncludes(): void {\n  if (!String.prototype.includes) {\n    String.prototype.includes = function (search: string, start?: number) {\n      if (typeof start !== 'number') {\n        start = 0;\n      }\n      if (start + search.length > this.length) {\n        return false;\n      }\n      return this.indexOf(search, start) !== -1;\n    };\n  }\n}\n\nexport function initializePolyfills(): void {\n  polyfillObjectAssign();\n  polyfillArrayFrom();\n  polyfillStringStartsWith();\n  polyfillStringEndsWith();\n  polyfillStringIncludes();\n  polyfillURLSearchParams();\n  polyfillTextEncoder();\n  polyfillPromiseFinally();\n}\n\n","import {\n  inferDeviceIdType,\n  isEquivalentDeviceIdType,\n} from \"./vastEnvironmentSignals\";\n\nexport interface VastConsentSignals {\n  gdpr?: string | undefined;\n  gdprConsent?: string | undefined;\n  usPrivacy?: string | undefined;\n}\n\nexport interface VastMacroContext {\n  correlator: string;\n  streamCorrelator: string;\n  pod?: number | undefined;\n  podMaxAds?: number | undefined;\n  podMinDurationMs?: number | undefined;\n  podMaxDurationMs?: number | undefined;\n  isCtv?: boolean | undefined;\n  contentUrl?: string | undefined;\n  pageUrl?: string | undefined;\n  adWillPlayMuted?: boolean | undefined;\n  adWillAutoPlay?: boolean | undefined;\n  appId?: string | undefined;\n  appName?: string | undefined;\n  sessionId?: string | undefined;\n  deviceId?: string | undefined;\n  deviceIdType?: string | undefined;\n  limitAdTracking?: boolean | undefined;\n  deviceTypeHint?: number | undefined;\n  adTest?: boolean | undefined;\n  consent?: VastConsentSignals | undefined;\n}\n\nconst UNEXPANDED_MACRO_PATTERN = /^(\\[[^\\]]*\\]|\\{[^}]*\\}|%%[^%]*%%)$/;\nconst INVALID_VAST_PARAM_KEY = /^\\s|\\s$/;\nconst EXAMPLE_COM_URL = /example\\.com/i;\nconst CTV_UNSUPPORTED_PARAMS = [\n  \"description_url\",\n  \"tfcd\",\n  \"npa\",\n  \"min_ad_duration\",\n  \"max_ad_duration\",\n  \"unviewed_position_start\",\n  \"impl\",\n  \"vad_type\",\n  \"gdpr\",\n  \"gdpr_consent\",\n  \"us_privacy\",\n];\n\nconst INLINE_DEVICE_MACRO_REPLACEMENTS: Array<{\n  pattern: RegExp;\n  getValue: (ctx: VastMacroContext) => string | undefined;\n}> = [\n  { pattern: /\\[RDID\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[IFA\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[ADVERTISING[_-]?ID(?:ENTIFIER)?\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[DEVICE[_-]?ID\\]/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\[IDTYPE\\]/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /\\{rdid\\}/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\{device[_-]?id\\}/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /\\{idtype\\}/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /%%ADVERTISING_IDENTIFIER_PLAIN%%/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /%%ADVERTISING_ID_OPT_OUT%%/gi, getValue: (ctx) =>\n      ctx.limitAdTracking != null ? (ctx.limitAdTracking ? \"1\" : \"0\") : undefined },\n  { pattern: /%%ADVERTISING_ID_TYPE%%/gi, getValue: (ctx) => ctx.deviceIdType },\n  { pattern: /%%ADVERTISING_ID%%/gi, getValue: (ctx) => ctx.deviceId },\n  { pattern: /%%LIMIT_AD_TRACKING%%/gi, getValue: (ctx) =>\n      ctx.limitAdTracking != null ? (ctx.limitAdTracking ? \"1\" : \"0\") : undefined },\n  { pattern: /%%MSID%%/gi, getValue: (ctx) => ctx.appId },\n  { pattern: /%%APP_NAME%%/gi, getValue: (ctx) => ctx.appName },\n  { pattern: /%%SESSION_ID%%/gi, getValue: (ctx) => ctx.sessionId },\n  { pattern: /%%CORRELATOR%%/gi, getValue: (ctx) => ctx.correlator },\n];\n\nexport function isMacroPlaceholder(value: string | null | undefined): boolean {\n  if (value == null) return true;\n  const trimmed = value.trim();\n  if (!trimmed) return true;\n  if (UNEXPANDED_MACRO_PATTERN.test(trimmed)) return true;\n  return /^(unknown|null|undefined|none|n\\/a|\\$\\{[^}]+\\})$/i.test(trimmed);\n}\n\nexport function generateCorrelator(): string {\n  if (typeof crypto !== \"undefined\" && crypto.getRandomValues) {\n    try {\n      const buf = new Uint32Array(2);\n      crypto.getRandomValues(buf);\n      const value = (buf[0] ?? 0) * 0x200000 + ((buf[1] ?? 0) & 0x1fffff);\n      if (value > 0) {\n        return String(value);\n      }\n    } catch {\n    }\n  }\n  return String(Math.floor(Math.random() * Number.MAX_SAFE_INTEGER) + 1);\n}\n\nfunction expandInlineMacroPlaceholders(baseUrl: string, ctx: VastMacroContext): string {\n  let url = baseUrl;\n  for (const { pattern, getValue } of INLINE_DEVICE_MACRO_REPLACEMENTS) {\n    const value = getValue(ctx);\n    if (value != null && value !== \"\") {\n      url = url.replace(pattern, encodeURIComponent(value));\n    }\n  }\n  return url;\n}\n\nfunction applyDeviceIdentityParams(\n  params: URLSearchParams,\n  ctx: VastMacroContext\n): void {\n  const runtimeId = ctx.deviceId?.trim();\n  const runtimeType = ctx.deviceIdType?.trim() || inferDeviceIdType();\n  const tagRdid = params.get(\"rdid\");\n  const tagType = params.get(\"idtype\");\n  const tagLat = params.get(\"is_lat\");\n  const latValue =\n    ctx.limitAdTracking != null ? (ctx.limitAdTracking ? \"1\" : \"0\") : undefined;\n\n  if (runtimeId) {\n    params.set(\"rdid\", runtimeId);\n    params.set(\"idtype\", runtimeType || tagType || \"aaid\");\n    params.set(\"is_lat\", latValue ?? (isMacroPlaceholder(tagLat) ? \"0\" : tagLat!));\n    return;\n  }\n\n  const tagRdidValid = Boolean(tagRdid && !isMacroPlaceholder(tagRdid));\n  const tagTypeValid = Boolean(tagType && !isMacroPlaceholder(tagType));\n\n  if (\n    tagRdidValid &&\n    tagTypeValid &&\n    runtimeType &&\n    !isEquivalentDeviceIdType(tagType!, runtimeType)\n  ) {\n    params.delete(\"rdid\");\n    params.delete(\"idtype\");\n    params.delete(\"is_lat\");\n    return;\n  }\n\n  if (tagRdidValid) {\n    if (isMacroPlaceholder(tagType) && runtimeType) {\n      params.set(\"idtype\", runtimeType);\n    }\n    if (isMacroPlaceholder(tagLat)) {\n      params.set(\"is_lat\", latValue ?? \"0\");\n    }\n    return;\n  }\n\n  params.delete(\"rdid\");\n  params.delete(\"idtype\");\n  params.delete(\"is_lat\");\n}\n\nfunction removeBrokenAppNameOrphans(\n  params: URLSearchParams,\n  appName?: string\n): void {\n  const toDelete: string[] = [];\n\n  params.forEach((_value, key) => {\n    if (!key || INVALID_VAST_PARAM_KEY.test(key)) {\n      toDelete.push(key);\n    }\n  });\n\n  if (appName && appName.includes(\"&\")) {\n    for (const suffix of appName.split(\"&\").slice(1)) {\n      const trimmed = suffix.replace(/^\\s+/, \"\");\n      if (!trimmed) continue;\n      toDelete.push(suffix, ` ${trimmed}`, trimmed);\n    }\n  }\n\n  for (const key of new Set(toDelete)) {\n    if (key) params.delete(key);\n  }\n}\n\nexport function normalizeVastTagUrl(raw: string): string {\n  if (!raw) return raw;\n\n  try {\n    const url = new URL(raw);\n\n    const anValue = url.searchParams.get(\"an\");\n    if (anValue !== null) {\n      const orphanFragments: string[] = [];\n      url.searchParams.forEach((_value, key) => {\n        if (key && INVALID_VAST_PARAM_KEY.test(key)) {\n          orphanFragments.push(key.trim());\n        }\n      });\n      if (orphanFragments.length > 0) {\n        const reconstructed = [anValue.replace(/\\s+$/, \"\"), ...orphanFragments]\n          .filter(Boolean)\n          .join(\" & \");\n\n        url.searchParams.forEach((_value, key) => {\n          if (key && INVALID_VAST_PARAM_KEY.test(key)) {\n            url.searchParams.delete(key);\n          }\n        });\n        url.searchParams.set(\"an\", reconstructed);\n\n        return url.toString().replace(\n          /([?&]an=)([^&]*)/,\n          (_match, prefix, val) => prefix + val.replace(/\\+/g, \"%20\")\n        );\n      }\n    }\n\n    removeBrokenAppNameOrphans(url.searchParams);\n    return url.toString();\n  } catch {\n    return raw;\n  }\n}\n\nexport function applyVastMacros(\n  baseUrl: string,\n  ctx: VastMacroContext\n): string {\n  const expandedUrl = expandInlineMacroPlaceholders(baseUrl, ctx);\n  let url: URL;\n  try {\n    url = new URL(normalizeVastTagUrl(expandedUrl));\n  } catch {\n    return replaceCorrelatorFallback(expandedUrl, ctx.correlator);\n  }\n\n  const params = url.searchParams;\n\n  removeBrokenAppNameOrphans(params, ctx.appName);\n\n  params.set(\"correlator\", ctx.correlator);\n  params.set(\"scor\", ctx.streamCorrelator);\n  if (ctx.isCtv) {\n    for (const key of CTV_UNSUPPORTED_PARAMS) {\n      params.delete(key);\n    }\n  }\n\n  if (ctx.pod != null) {\n    params.set(\"pod\", String(ctx.pod));\n  }\n\n  params.delete(\"ppos\");\n  params.delete(\"lip\");\n  if (ctx.podMinDurationMs != null) {\n    params.set(\"pmnd\", String(Math.max(0, Math.round(ctx.podMinDurationMs))));\n  }\n  if (ctx.podMaxDurationMs != null) {\n    params.set(\"pmxd\", String(Math.max(0, Math.round(ctx.podMaxDurationMs))));\n  }\n  if (ctx.podMaxAds != null) {\n    params.set(\"pmad\", String(Math.max(1, Math.round(ctx.podMaxAds))));\n  }\n\n  const requestUrl = ctx.contentUrl || ctx.pageUrl;\n  if (requestUrl) {\n    params.set(\"url\", requestUrl);\n    if (!ctx.isCtv) {\n      params.set(\"description_url\", requestUrl);\n    }\n  } else {\n    const existingUrl = params.get(\"url\") || \"\";\n    if (EXAMPLE_COM_URL.test(existingUrl)) {\n      params.delete(\"url\");\n      params.delete(\"description_url\");\n    }\n  }\n\n  if (ctx.adWillPlayMuted != null) {\n    params.set(\"vpmute\", ctx.adWillPlayMuted ? \"1\" : \"0\");\n  }\n  if (ctx.adWillAutoPlay != null) {\n    params.set(\"vpa\", ctx.adWillAutoPlay ? \"auto\" : \"click\");\n  }\n\n  if (ctx.appId) {\n    params.set(\"msid\", ctx.appId);\n  }\n  if (ctx.appName) {\n    removeBrokenAppNameOrphans(params, ctx.appName);\n    params.set(\"an\", ctx.appName);\n  }\n  if (ctx.sessionId) {\n    params.set(\"sid\", ctx.sessionId);\n  }\n  if (ctx.deviceTypeHint != null) {\n    params.set(\"dth\", String(ctx.deviceTypeHint));\n  } else if (ctx.isCtv) {\n    params.set(\"dth\", \"5\");\n  }\n\n  applyDeviceIdentityParams(params, ctx);\n\n  if (!ctx.isCtv) {\n    const consent = ctx.consent;\n    if (consent?.gdpr != null) {\n      params.set(\"gdpr\", consent.gdpr);\n    }\n    if (consent?.gdprConsent != null) {\n      params.set(\"gdpr_consent\", consent.gdprConsent);\n    }\n    if (consent?.usPrivacy != null) {\n      params.set(\"us_privacy\", consent.usPrivacy);\n    }\n  }\n\n  if (ctx.adTest) {\n    params.set(\"adtest\", \"on\");\n  }\n\n  const staleKeys: string[] = [];\n  params.forEach((value, key) => {\n    if (isMacroPlaceholder(value)) {\n      staleKeys.push(key);\n    }\n  });\n  for (const key of staleKeys) {\n    params.delete(key);\n  }\n\n  removeBrokenAppNameOrphans(params, ctx.appName);\n\n  return url.toString();\n}\n\nfunction replaceCorrelatorFallback(baseUrl: string, correlator: string): string {\n  const correlatorRegex = /([?&])correlator=([^&]*)/;\n  if (correlatorRegex.test(baseUrl)) {\n    return baseUrl.replace(correlatorRegex, `$1correlator=${correlator}`);\n  }\n  const sep = baseUrl.includes(\"?\") ? \"&\" : \"?\";\n  return `${baseUrl}${sep}correlator=${correlator}`;\n}\n\nexport function fetchConsentSignals(\n  timeoutMs: number = 1500\n): Promise<VastConsentSignals> {\n  const signals: VastConsentSignals = {};\n  if (typeof window === \"undefined\") {\n    return Promise.resolve(signals);\n  }\n\n  const tasks: Promise<void>[] = [];\n\n  const tcfApi = (window as any).__tcfapi;\n  if (typeof tcfApi === \"function\") {\n    tasks.push(\n      new Promise<void>((resolve) => {\n        let settled = false;\n        try {\n          tcfApi(\"addEventListener\", 2, (tcData: any, success: boolean) => {\n            if (settled) return;\n            if (\n              success &&\n              tcData &&\n              (tcData.eventStatus === \"tcloaded\" ||\n                tcData.eventStatus === \"useractioncomplete\")\n            ) {\n              settled = true;\n              signals.gdpr = tcData.gdprApplies ? \"1\" : \"0\";\n              if (typeof tcData.tcString === \"string\" && tcData.tcString) {\n                signals.gdprConsent = tcData.tcString;\n              }\n              try {\n                tcfApi(\"removeEventListener\", 2, () => {}, tcData.listenerId);\n              } catch {}\n              resolve();\n            }\n          });\n        } catch {\n          resolve();\n        }\n        setTimeout(() => {\n          if (!settled) {\n            settled = true;\n            resolve();\n          }\n        }, timeoutMs);\n      })\n    );\n  }\n\n  const uspApi = (window as any).__uspapi;\n  if (typeof uspApi === \"function\") {\n    tasks.push(\n      new Promise<void>((resolve) => {\n        try {\n          uspApi(\"getUSPData\", 1, (data: any, success: boolean) => {\n            if (success && typeof data?.uspString === \"string\" && data.uspString) {\n              signals.usPrivacy = data.uspString;\n            }\n            resolve();\n          });\n        } catch {\n          resolve();\n        }\n        setTimeout(resolve, timeoutMs);\n      })\n    );\n  }\n\n  if (tasks.length === 0) {\n    return Promise.resolve(signals);\n  }\n\n  return Promise.all(tasks).then(() => signals);\n}\n","interface NavigatorUAData {\n  platform?: string;\n  brands?: Array<{ brand: string; version: string }>;\n  mobile?: boolean;\n}\n\ndeclare global {\n  interface Navigator {\n    userAgentData?: NavigatorUAData;\n  }\n}\n\nexport interface BrowserInfo {\n  name: string;\n  version: string;\n  majorVersion: number;\n  isSmartTV: boolean;\n  isLegacyTV: boolean;\n  platform: string;\n  supportsModernJS: boolean;\n  webOSVersion?: number | undefined;\n  tizenVersion?: number | undefined;\n  chromeVersion?: number | undefined;\n}\n\nfunction getChromeVersion(ua: string): number {\n  const match = ua.match(/Chrome\\/(\\d+)/);\n  return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getWebKitVersion(ua: string): number {\n  const match = ua.match(/AppleWebKit\\/(\\d+)/);\n  return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getPlatform(): string {\n  if ('userAgentData' in navigator && navigator.userAgentData?.platform) {\n    return navigator.userAgentData.platform;\n  }\n\n  const ua = navigator.userAgent;\n  if (/Mac|iPhone|iPad|iPod/i.test(ua)) {\n    return /iPhone|iPad|iPod/i.test(ua) ? 'iPhone' : 'MacIntel';\n  }\n  if (/Win/i.test(ua)) {\n    return 'Win32';\n  }\n  if (/Linux/i.test(ua)) {\n    return /Android/i.test(ua) ? 'Linux armv8l' : 'Linux x86_64';\n  }\n  if (/CrOS/i.test(ua)) {\n    return 'CrOS';\n  }\n\n  // eslint-disable-next-line deprecation/deprecation\n  return (navigator as any).platform || 'Unknown';\n}\n\nexport function detectBrowser(): BrowserInfo {\n  const ua = navigator.userAgent;\n  const platform = getPlatform();\n\n  let name = 'Unknown';\n  let version = '0';\n  let majorVersion = 0;\n  let isSmartTV = false;\n  let isLegacyTV = false;\n  let supportsModernJS = true;\n  let webOSVersion: number | undefined;\n  let tizenVersion: number | undefined;\n  let chromeVersionNum: number | undefined;\n\n  const chromeVersion = getChromeVersion(ua);\n  const webkitVersion = getWebKitVersion(ua);\n  chromeVersionNum = chromeVersion > 0 ? chromeVersion : undefined;\n\n  if (/Web0S|webOS|LG Browser|LGSTB/i.test(ua)) {\n    name = 'LG WebOS';\n    isSmartTV = true;\n\n    let match = ua.match(/Web0S[/\\s]*([\\d.]+)/i) || ua.match(/webOS[/\\s]*([\\d.]+)/i);\n\n    if (!match || !match[1]) {\n      match = ua.match(/webOSTV[/\\s-]*([\\d.]+)/i) || ua.match(/webOS\\.TV[/\\s-]*([\\d.]+)/i);\n    }\n\n    if (match && match[1]) {\n      version = match[1];\n      const parts = version.split('.');\n      majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n      webOSVersion = majorVersion;\n    } else if (chromeVersion > 0) {\n      if (chromeVersion >= 79) {\n        webOSVersion = 6;\n        version = '6.0';\n        majorVersion = 6;\n      } else if (chromeVersion >= 68) {\n        webOSVersion = 5;\n        version = '5.0';\n        majorVersion = 5;\n      } else if (chromeVersion >= 53) {\n        webOSVersion = 4;\n        version = '4.0';\n        majorVersion = 4;\n      } else if (chromeVersion >= 38) {\n        webOSVersion = 3;\n        version = '3.0';\n        majorVersion = 3;\n      } else {\n        webOSVersion = 2;\n        version = '2.0';\n        majorVersion = 2;\n      }\n    } else {\n      version = 'Unknown';\n      webOSVersion = undefined;\n    }\n\n    isLegacyTV = webOSVersion !== undefined && webOSVersion < 3;\n  } else if (/Tizen/i.test(ua)) {\n    name = 'Samsung Tizen';\n    isSmartTV = true;\n    const match = ua.match(/Tizen[/\\s]*([\\d.]+)/i);\n    version = match && match[1] ? match[1] : 'Unknown';\n    if (version !== 'Unknown') {\n      const parts = version.split('.');\n      majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n      tizenVersion = majorVersion;\n    }\n\n    isLegacyTV = tizenVersion !== undefined && tizenVersion < 3;\n  } else if (/SMART-TV|SmartTV/i.test(ua)) {\n    name = 'Smart TV';\n    isSmartTV = true;\n    isLegacyTV = chromeVersion > 0 && chromeVersion < 53;\n  } else if (/NetCast/i.test(ua)) {\n    name = 'LG NetCast';\n    isSmartTV = true;\n    isLegacyTV = true;\n  } else if (/BRAVIA/i.test(ua)) {\n    name = 'Sony BRAVIA';\n    isSmartTV = true;\n    isLegacyTV = chromeVersion > 0 && chromeVersion < 53;\n  } else {\n    if (chromeVersion > 0) {\n      name = 'Chrome';\n      version = chromeVersion.toString();\n      majorVersion = chromeVersion;\n\n      if (chromeVersion < 50) {\n        supportsModernJS = false;\n      }\n    }\n\n    if (webkitVersion > 0 && webkitVersion < 600) {\n      supportsModernJS = false;\n    }\n  }\n\n  if (typeof Promise === 'undefined' ||\n      typeof Map === 'undefined' ||\n      typeof Set === 'undefined') {\n    supportsModernJS = false;\n  }\n\n  if (typeof URLSearchParams === 'undefined') {\n    supportsModernJS = false;\n  }\n\n  return {\n    name,\n    version,\n    majorVersion,\n    isSmartTV,\n    isLegacyTV,\n    platform,\n    supportsModernJS,\n    webOSVersion,\n    tizenVersion,\n    chromeVersion: chromeVersionNum,\n  };\n}\n\nexport function getBrowserConfigOverrides(): {\n  allowNativeHls?: boolean;\n  pauseContentDuringAds?: boolean;\n} {\n  const browser = detectBrowser();\n  const overrides: {\n    allowNativeHls?: boolean;\n    pauseContentDuringAds?: boolean;\n  } = {};\n\n  if (browser.isSmartTV) {\n    overrides.allowNativeHls = true;\n    overrides.pauseContentDuringAds = true;\n  }\n\n  return overrides;\n}\n\nexport function supportsModernJS(): boolean {\n  try {\n    return (\n      typeof Promise !== 'undefined' &&\n      typeof Map !== 'undefined' &&\n      typeof Set !== 'undefined' &&\n      typeof Array.from !== 'undefined' &&\n      typeof Object.assign !== 'undefined' &&\n      typeof Array.prototype.forEach !== 'undefined' &&\n      typeof String.prototype.includes !== 'undefined'\n    );\n  } catch (e) {\n    return false;\n  }\n}\n\nexport function logBrowserInfo(debug: boolean = false): void {\n  if (!debug) return;\n\n  const browser = detectBrowser();\n\n  console.log('[StormcloudVideoPlayer] Browser Compatibility Info:', {\n    browser: `${browser.name} ${browser.version}`,\n    platform: browser.platform,\n    isSmartTV: browser.isSmartTV,\n    isLegacyTV: browser.isLegacyTV,\n    supportsModernJS: browser.supportsModernJS,\n    ...(browser.webOSVersion !== undefined ? { webOSVersion: browser.webOSVersion } : {}),\n    ...(browser.tizenVersion !== undefined ? { tizenVersion: browser.tizenVersion } : {}),\n    ...(browser.chromeVersion !== undefined ? { chromeVersion: browser.chromeVersion } : {}),\n    userAgent: navigator.userAgent,\n  });\n}\n\nexport function supportsFeature(feature: string): boolean {\n  switch (feature) {\n    case 'urlsearchparams':\n      return typeof URLSearchParams !== 'undefined';\n    case 'textencoder':\n      return typeof TextEncoder !== 'undefined';\n    case 'promises':\n      return typeof Promise !== 'undefined';\n    case 'fetch':\n      return typeof fetch !== 'undefined';\n    case 'crypto':\n      return typeof crypto !== 'undefined' && typeof crypto.subtle !== 'undefined';\n    default:\n      return false;\n  }\n}\n","import type { Scte35Marker, Id3TagInfo } from \"../types\";\n\nexport function parseCueOutDuration(value: string): number | undefined {\n  const num = parseFloat(value.trim());\n  if (!Number.isNaN(num)) return num;\n  const match =\n    value.match(/(?:^|[,\\s])DURATION\\s*=\\s*([0-9.]+)/i) ||\n    value.match(/Duration\\s*=\\s*([0-9.]+)/i);\n  if (match && match[1] != null) {\n    const dStr = match[1];\n    const d = parseFloat(dStr);\n    return Number.isNaN(d) ? undefined : d;\n  }\n  return undefined;\n}\n\nexport function parseCueOutCont(\n  value: string\n): { elapsed?: number; duration?: number } | undefined {\n  const res: { elapsed?: number; duration?: number } = {};\n\n  const elapsedMatch = value.match(/Elapsed\\s*=\\s*([0-9.]+)/i);\n  const durationMatch = value.match(/Duration\\s*=\\s*([0-9.]+)/i);\n  if (elapsedMatch && elapsedMatch[1] != null) {\n    const e = parseFloat(elapsedMatch[1]);\n    if (!Number.isNaN(e)) res.elapsed = e;\n  }\n  if (durationMatch && durationMatch[1] != null) {\n    const d = parseFloat(durationMatch[1]);\n    if (!Number.isNaN(d)) res.duration = d;\n  }\n\n  if (!(\"elapsed\" in res) || !(\"duration\" in res)) {\n    const slashMatch = value.match(/([0-9.]+)\\s*\\/\\s*([0-9.]+)/);\n    if (slashMatch && slashMatch[1] && slashMatch[2]) {\n      const elapsed = parseFloat(slashMatch[1]);\n      const duration = parseFloat(slashMatch[2]);\n      if (!Number.isNaN(elapsed) && !(\"elapsed\" in res)) res.elapsed = elapsed;\n      if (!Number.isNaN(duration) && !(\"duration\" in res)) res.duration = duration;\n    }\n  }\n\n  if (\"elapsed\" in res || \"duration\" in res) return res;\n  return undefined;\n}\n\nexport function parseAttributeList(value: string): Record<string, string> {\n  const attrs: Record<string, string> = {};\n  const regex = /([A-Z0-9-]+)=((\"[^\"]*\")|([^\",]*))(?:,|$)/gi;\n  let match: RegExpExecArray | null;\n  while ((match = regex.exec(value)) !== null) {\n    const key: string = (match[1] ?? \"\") as string;\n    let rawVal: string = (match[3] ?? match[4] ?? \"\") as string;\n    if (rawVal.startsWith('\"') && rawVal.endsWith('\"')) {\n      rawVal = rawVal.slice(1, -1);\n    }\n    if (key) {\n      attrs[key] = rawVal;\n    }\n  }\n  return attrs;\n}\n\nexport function toNumber(val: unknown): number | undefined {\n  if (val == null) return undefined;\n  const n = typeof val === \"string\" ? parseFloat(val) : Number(val);\n  return Number.isNaN(n) ? undefined : n;\n}\n\nexport function isManifestBasedMarker(marker: Scte35Marker): boolean {\n  const raw = marker.raw as any;\n  if (!raw) return false;\n\n  if (raw.tag) {\n    const tag = String(raw.tag);\n    return (\n      tag.includes(\"EXT-X-CUE-OUT\") ||\n      tag.includes(\"EXT-X-CUE-IN\") ||\n      tag.includes(\"EXT-X-DATERANGE\")\n    );\n  }\n\n  if (raw.id3) return false;\n\n  if (raw.splice_command_type) return false;\n\n  return false;\n}\n\nexport function decodeId3ValueToText(value: string | Uint8Array): string | undefined {\n  try {\n    if (typeof value === \"string\") return value;\n    const decoder = new TextDecoder(\"utf-8\", { fatal: false });\n    const text = decoder.decode(value);\n    if (text && /[\\x20-\\x7E]/.test(text)) return text;\n    let out = \"\";\n    for (let i = 0; i < value.length; i++)\n      out += String.fromCharCode(value[i]!);\n    return out;\n  } catch {\n    return undefined;\n  }\n}\n\nexport function getFragmentStartSeconds(frag: any): number | undefined {\n  const candidates = [frag?.start, frag?.startPTS];\n  for (const candidate of candidates) {\n    if (typeof candidate === \"number\" && Number.isFinite(candidate)) {\n      return candidate;\n    }\n  }\n  return undefined;\n}\n\nexport function parseScte35FromId3(tag: Id3TagInfo): Scte35Marker | undefined {\n  const text = decodeId3ValueToText(tag.value);\n  if (!text) return undefined;\n\n  const cueOutMatch =\n    text.match(/EXT-X-CUE-OUT(?::([^\\r\\n]*))?/i) ||\n    text.match(/CUE-OUT(?::([^\\r\\n]*))?/i);\n  if (cueOutMatch) {\n    const arg = (cueOutMatch[1] ?? \"\").trim();\n    const dur = parseCueOutDuration(arg);\n    const marker: Scte35Marker = {\n      type: \"start\",\n      ...(tag.ptsSeconds !== undefined ? { ptsSeconds: tag.ptsSeconds } : {}),\n      ...(dur !== undefined ? { durationSeconds: dur } : {}),\n      raw: { id3: text },\n    } as Scte35Marker;\n    return marker;\n  }\n\n  const cueOutContMatch = text.match(/EXT-X-CUE-OUT-CONT:([^\\r\\n]*)/i);\n  if (cueOutContMatch) {\n    const arg = (cueOutContMatch[1] ?? \"\").trim();\n    const cont = parseCueOutCont(arg);\n    const marker: Scte35Marker = {\n      type: \"progress\",\n      ...(tag.ptsSeconds !== undefined ? { ptsSeconds: tag.ptsSeconds } : {}),\n      ...(cont?.duration !== undefined\n        ? { durationSeconds: cont.duration }\n        : {}),\n      raw: { id3: text },\n    } as Scte35Marker;\n    return marker;\n  }\n\n  const cueInMatch = text.match(/EXT-X-CUE-IN\\b/i) || text.match(/CUE-IN\\b/i);\n  if (cueInMatch) {\n    const marker: Scte35Marker = {\n      type: \"end\",\n      ...(tag.ptsSeconds !== undefined ? { ptsSeconds: tag.ptsSeconds } : {}),\n      raw: { id3: text },\n    } as Scte35Marker;\n    return marker;\n  }\n\n  const daterangeMatch = text.match(/EXT-X-DATERANGE:([^\\r\\n]*)/i);\n  if (daterangeMatch) {\n    const attrs = parseAttributeList(daterangeMatch[1] ?? \"\");\n    const hasScteOut =\n      \"SCTE35-OUT\" in attrs || attrs[\"SCTE35-OUT\"] !== undefined;\n    const hasScteIn =\n      \"SCTE35-IN\" in attrs || attrs[\"SCTE35-IN\"] !== undefined;\n    const klass = String(attrs[\"CLASS\"] ?? \"\");\n    const duration = toNumber(attrs[\"DURATION\"]);\n    if (hasScteOut || /com\\.apple\\.hls\\.cue/i.test(klass)) {\n      const marker: Scte35Marker = {\n        type: \"start\",\n        ...(tag.ptsSeconds !== undefined\n          ? { ptsSeconds: tag.ptsSeconds }\n          : {}),\n        ...(duration !== undefined ? { durationSeconds: duration } : {}),\n        raw: { id3: text, attrs },\n      } as Scte35Marker;\n      return marker;\n    }\n    if (hasScteIn) {\n      const marker: Scte35Marker = {\n        type: \"end\",\n        ...(tag.ptsSeconds !== undefined\n          ? { ptsSeconds: tag.ptsSeconds }\n          : {}),\n        raw: { id3: text, attrs },\n      } as Scte35Marker;\n      return marker;\n    }\n  }\n\n  if (/SCTE35-OUT/i.test(text)) {\n    const marker: Scte35Marker = {\n      type: \"start\",\n      ...(tag.ptsSeconds !== undefined ? { ptsSeconds: tag.ptsSeconds } : {}),\n      raw: { id3: text },\n    } as Scte35Marker;\n    return marker;\n  }\n  if (/SCTE35-IN/i.test(text)) {\n    const marker: Scte35Marker = {\n      type: \"end\",\n      ...(tag.ptsSeconds !== undefined ? { ptsSeconds: tag.ptsSeconds } : {}),\n      raw: { id3: text },\n    } as Scte35Marker;\n    return marker;\n  }\n\n  if (tag.value instanceof Uint8Array) {\n    const bin = parseScte35Binary(tag.value);\n    if (bin) return bin;\n  }\n\n  return undefined;\n}\n\nexport function normalizeFragmentPayload(payload: unknown): Uint8Array | undefined {\n  if (payload instanceof Uint8Array) {\n    return payload;\n  }\n  if (payload instanceof ArrayBuffer) {\n    return new Uint8Array(payload);\n  }\n  if (ArrayBuffer.isView(payload)) {\n    const view = payload as ArrayBufferView;\n    return new Uint8Array(view.buffer, view.byteOffset, view.byteLength);\n  }\n  return undefined;\n}\n\n// --- Transport Stream SCTE-35 parsing ---\n\nexport function detectTsPacketFormat(\n  data: Uint8Array\n): { offset: number; packetSize: number; tsPayloadOffset: number } | undefined {\n  const packetSizes = [188, 192, 204];\n  for (const packetSize of packetSizes) {\n    const tsPayloadOffset = packetSize === 192 ? 4 : 0;\n    for (let offset = 0; offset < packetSize; offset++) {\n      let matchedPackets = 0;\n      for (\n        let packetStart = offset;\n        packetStart + tsPayloadOffset < data.length &&\n        matchedPackets < 5;\n        packetStart += packetSize\n      ) {\n        if (data[packetStart + tsPayloadOffset] !== 0x47) {\n          break;\n        }\n        matchedPackets++;\n      }\n      if (matchedPackets >= 2) {\n        return { offset, packetSize, tsPayloadOffset };\n      }\n    }\n  }\n  return undefined;\n}\n\nfunction getPsiSectionStart(\n  payload: Uint8Array,\n  payloadUnitStart: boolean\n): number | undefined {\n  if (!payloadUnitStart) {\n    return undefined;\n  }\n  const pointerField = payload[0];\n  if (pointerField == null) {\n    return undefined;\n  }\n  const sectionStart = 1 + pointerField;\n  return sectionStart < payload.length ? sectionStart : undefined;\n}\n\nfunction getPsiSectionLength(data: Uint8Array, offset: number): number {\n  return (((data[offset + 1] ?? 0) & 0x0f) << 8) | (data[offset + 2] ?? 0);\n}\n\nfunction parsePatSection(\n  payload: Uint8Array,\n  payloadUnitStart: boolean,\n  pmtPids: Set<number>\n): void {\n  const sectionStart = getPsiSectionStart(payload, payloadUnitStart);\n  if (sectionStart == null || sectionStart + 8 >= payload.length) {\n    return;\n  }\n  if (payload[sectionStart] !== 0x00) {\n    return;\n  }\n\n  const sectionLength = getPsiSectionLength(payload, sectionStart);\n  const sectionEnd = Math.min(\n    payload.length,\n    sectionStart + 3 + sectionLength\n  );\n\n  for (let offset = sectionStart + 8; offset + 4 <= sectionEnd - 4; offset += 4) {\n    const programNumber =\n      ((payload[offset] ?? 0) << 8) | (payload[offset + 1] ?? 0);\n    const pid =\n      (((payload[offset + 2] ?? 0) & 0x1f) << 8) |\n      (payload[offset + 3] ?? 0);\n    if (programNumber !== 0) {\n      pmtPids.add(pid);\n    }\n  }\n}\n\nfunction descriptorsIdentifyScte35(\n  data: Uint8Array,\n  start: number,\n  end: number\n): boolean {\n  let offset = start;\n  while (offset + 2 <= end) {\n    const tag = data[offset] ?? 0;\n    const length = data[offset + 1] ?? 0;\n    const descriptorStart = offset + 2;\n    const descriptorEnd = descriptorStart + length;\n    if (descriptorEnd > end) {\n      return false;\n    }\n\n    const registration =\n      length >= 4\n        ? String.fromCharCode(\n            data[descriptorStart] ?? 0,\n            data[descriptorStart + 1] ?? 0,\n            data[descriptorStart + 2] ?? 0,\n            data[descriptorStart + 3] ?? 0\n          )\n        : \"\";\n    if (tag === 0x8a || registration === \"CUEI\" || registration === \"SCTE\") {\n      return true;\n    }\n\n    offset = descriptorEnd;\n  }\n  return false;\n}\n\nfunction parsePmtSection(\n  payload: Uint8Array,\n  payloadUnitStart: boolean,\n  tsScte35Pids: Set<number>\n): void {\n  const sectionStart = getPsiSectionStart(payload, payloadUnitStart);\n  if (sectionStart == null || sectionStart + 12 >= payload.length) {\n    return;\n  }\n  if (payload[sectionStart] !== 0x02) {\n    return;\n  }\n\n  const sectionLength = getPsiSectionLength(payload, sectionStart);\n  const sectionEnd = Math.min(\n    payload.length,\n    sectionStart + 3 + sectionLength\n  );\n  const programInfoLength =\n    (((payload[sectionStart + 10] ?? 0) & 0x0f) << 8) |\n    (payload[sectionStart + 11] ?? 0);\n\n  let offset = sectionStart + 12 + programInfoLength;\n  while (offset + 5 <= sectionEnd - 4) {\n    const streamType = payload[offset] ?? 0;\n    const elementaryPid =\n      (((payload[offset + 1] ?? 0) & 0x1f) << 8) |\n      (payload[offset + 2] ?? 0);\n    const esInfoLength =\n      (((payload[offset + 3] ?? 0) & 0x0f) << 8) |\n      (payload[offset + 4] ?? 0);\n    const descriptorStart = offset + 5;\n    const descriptorEnd = Math.min(descriptorStart + esInfoLength, sectionEnd - 4);\n\n    if (\n      streamType === 0x86 ||\n      (streamType === 0x06 &&\n        descriptorsIdentifyScte35(payload, descriptorStart, descriptorEnd))\n    ) {\n      tsScte35Pids.add(elementaryPid);\n    }\n\n    offset = descriptorStart + esInfoLength;\n  }\n}\n\nfunction hasProcessedTsScte35Section(\n  section: Uint8Array,\n  processedSections: Set<string>\n): boolean {\n  let checksum = 0;\n  for (let i = 0; i < section.length; i++) {\n    checksum = (checksum * 31 + (section[i] ?? 0)) >>> 0;\n  }\n\n  const key = `${section.length}:${checksum}`;\n  if (processedSections.has(key)) {\n    return true;\n  }\n\n  processedSections.add(key);\n  if (processedSections.size > 200) {\n    const firstKey = processedSections.values().next().value;\n    if (firstKey) {\n      processedSections.delete(firstKey);\n    }\n  }\n  return false;\n}\n\nfunction addScte35SectionMarker(\n  section: Uint8Array,\n  markers: Scte35Marker[],\n  processedSections: Set<string>\n): void {\n  if (section[0] !== 0xfc || hasProcessedTsScte35Section(section, processedSections)) {\n    return;\n  }\n\n  const marker = parseScte35Binary(section);\n  if (!marker) {\n    return;\n  }\n\n  marker.raw = {\n    ...(typeof marker.raw === \"object\" && marker.raw ? marker.raw : {}),\n    source: \"ts-packet\",\n  };\n  markers.push(marker);\n}\n\nfunction appendScte35Bytes(\n  pid: number,\n  bytes: Uint8Array,\n  assemblers: Map<number, { bytes: number[]; expectedLength: number }>,\n  markers: Scte35Marker[],\n  processedSections: Set<string>\n): void {\n  const assembler = assemblers.get(pid);\n  if (!assembler) {\n    return;\n  }\n\n  for (let i = 0; i < bytes.length && assembler.bytes.length < assembler.expectedLength; i++) {\n    assembler.bytes.push(bytes[i] ?? 0);\n  }\n\n  if (assembler.bytes.length >= assembler.expectedLength) {\n    assemblers.delete(pid);\n    addScte35SectionMarker(new Uint8Array(assembler.bytes), markers, processedSections);\n  }\n}\n\nfunction collectScte35SectionsFromPayload(\n  pid: number,\n  payload: Uint8Array,\n  payloadUnitStart: boolean,\n  assemblers: Map<number, { bytes: number[]; expectedLength: number }>,\n  markers: Scte35Marker[],\n  processedSections: Set<string>\n): void {\n  if (payload.length === 0) {\n    return;\n  }\n\n  let offset = 0;\n  if (payloadUnitStart) {\n    const pointerField = payload[0] ?? 0;\n    const previousAssembler = assemblers.get(pid);\n    if (previousAssembler && pointerField > 0) {\n      appendScte35Bytes(\n        pid,\n        payload.subarray(1, Math.min(1 + pointerField, payload.length)),\n        assemblers,\n        markers,\n        processedSections\n      );\n    }\n    assemblers.delete(pid);\n    offset = 1 + pointerField;\n  } else {\n    appendScte35Bytes(pid, payload, assemblers, markers, processedSections);\n    return;\n  }\n\n  while (offset + 3 <= payload.length) {\n    const tableId = payload[offset];\n    if (tableId == null || tableId === 0xff) {\n      return;\n    }\n\n    const sectionLength = getPsiSectionLength(payload, offset);\n    const totalLength = 3 + sectionLength;\n    if (sectionLength <= 0 || totalLength <= 3) {\n      return;\n    }\n\n    if (offset + totalLength <= payload.length) {\n      addScte35SectionMarker(\n        payload.subarray(offset, offset + totalLength),\n        markers,\n        processedSections\n      );\n      offset += totalLength;\n    } else {\n      assemblers.set(pid, {\n        bytes: Array.from(payload.subarray(offset)),\n        expectedLength: totalLength,\n      });\n      return;\n    }\n  }\n}\n\nexport function parseScte35FromTsPackets(\n  data: Uint8Array,\n  tsScte35Pids: Set<number>,\n  pmtPids: Set<number>,\n  processedSections: Set<string>\n): Scte35Marker[] {\n  const packetInfo = detectTsPacketFormat(data);\n  if (!packetInfo) {\n    return [];\n  }\n\n  const markers: Scte35Marker[] = [];\n  const sectionAssemblers = new Map<\n    number,\n    { bytes: number[]; expectedLength: number }\n  >();\n\n  for (\n    let packetStart = packetInfo.offset;\n    packetStart + packetInfo.packetSize <= data.length;\n    packetStart += packetInfo.packetSize\n  ) {\n    const tsStart = packetStart + packetInfo.tsPayloadOffset;\n    if (data[tsStart] !== 0x47) {\n      continue;\n    }\n\n    const secondByte = data[tsStart + 1];\n    const thirdByte = data[tsStart + 2];\n    const fourthByte = data[tsStart + 3];\n    if (\n      secondByte == null ||\n      thirdByte == null ||\n      fourthByte == null ||\n      (secondByte & 0x80) !== 0\n    ) {\n      continue;\n    }\n\n    const payloadUnitStart = (secondByte & 0x40) !== 0;\n    const pid = ((secondByte & 0x1f) << 8) | thirdByte;\n    const adaptationFieldControl = (fourthByte >> 4) & 0x03;\n    const hasPayload =\n      adaptationFieldControl === 1 || adaptationFieldControl === 3;\n    if (!hasPayload) {\n      continue;\n    }\n\n    let payloadStart = tsStart + 4;\n    if (adaptationFieldControl === 3) {\n      const adaptationLength = data[payloadStart];\n      if (adaptationLength == null) {\n        continue;\n      }\n      payloadStart += 1 + adaptationLength;\n    }\n\n    const payloadEnd = Math.min(tsStart + 188, data.length);\n    if (payloadStart >= payloadEnd || payloadStart >= data.length) {\n      continue;\n    }\n\n    const payload = data.subarray(payloadStart, payloadEnd);\n    if (pid === 0) {\n      parsePatSection(payload, payloadUnitStart, pmtPids);\n    } else if (pmtPids.has(pid)) {\n      parsePmtSection(payload, payloadUnitStart, tsScte35Pids);\n    } else if (tsScte35Pids.has(pid)) {\n      collectScte35SectionsFromPayload(\n        pid,\n        payload,\n        payloadUnitStart,\n        sectionAssemblers,\n        markers,\n        processedSections\n      );\n    }\n  }\n\n  return markers;\n}\n\n// --- Binary SCTE-35 parsing ---\n\nclass BitReader {\n  private bytePos = 0;\n  private bitPos = 0;\n  constructor(private readonly buf: Uint8Array) {}\n  readBits(numBits: number): number {\n    let result = 0;\n    while (numBits > 0) {\n      if (this.bytePos >= this.buf.length) return result;\n      const remainingInByte = 8 - this.bitPos;\n      const toRead = Math.min(numBits, remainingInByte);\n      const currentByte = this.buf[this.bytePos]!;\n      const shift = remainingInByte - toRead;\n      const mask = ((1 << toRead) - 1) & 0xff;\n      const bits = (currentByte >> shift) & mask;\n      result = (result << toRead) | bits;\n      this.bitPos += toRead;\n      if (this.bitPos >= 8) {\n        this.bitPos = 0;\n        this.bytePos += 1;\n      }\n      numBits -= toRead;\n    }\n    return result >>> 0;\n  }\n  skipBits(n: number): void {\n    this.readBits(n);\n  }\n  get bytePosition(): number {\n    return this.bitPos === 0 ? this.bytePos : this.bytePos + 1;\n  }\n}\n\nfunction readSpliceTime(\n  r: BitReader,\n  ptsAdjustmentTicks: number\n): number | undefined {\n  const timeSpecifiedFlag = r.readBits(1) === 1;\n  if (!timeSpecifiedFlag) {\n    r.readBits(7);\n    return undefined;\n  }\n  r.readBits(6);\n  const high = r.readBits(1);\n  const low = r.readBits(32);\n  const ptsTicks =\n    (high * 0x100000000 + low + ptsAdjustmentTicks) % 0x200000000;\n  return ptsTicks / 90000;\n}\n\nfunction markerTypeFromSegmentationTypeId(\n  segmentationTypeId: number\n): Scte35Marker[\"type\"] | undefined {\n  switch (segmentationTypeId) {\n    case 0x10:\n    case 0x22:\n    case 0x30:\n    case 0x32:\n    case 0x34:\n    case 0x36:\n      return \"start\";\n    case 0x11:\n    case 0x23:\n    case 0x31:\n    case 0x33:\n    case 0x35:\n    case 0x37:\n      return \"end\";\n    default:\n      return undefined;\n  }\n}\n\nfunction parseScte35SegmentationDescriptor(\n  descriptor: Uint8Array\n):\n  | {\n      type: Scte35Marker[\"type\"];\n      durationSeconds?: number;\n      segmentationEventId?: number;\n    }\n  | undefined {\n  if (descriptor.length < 11) {\n    return undefined;\n  }\n\n  const identifier = String.fromCharCode(\n    descriptor[0] ?? 0,\n    descriptor[1] ?? 0,\n    descriptor[2] ?? 0,\n    descriptor[3] ?? 0\n  );\n  if (identifier !== \"CUEI\") {\n    return undefined;\n  }\n\n  const segmentationEventId =\n    ((descriptor[4] ?? 0) * 0x1000000) +\n    ((descriptor[5] ?? 0) << 16) +\n    ((descriptor[6] ?? 0) << 8) +\n    (descriptor[7] ?? 0);\n  const cancelIndicator = ((descriptor[8] ?? 0) & 0x80) !== 0;\n  if (cancelIndicator) {\n    return undefined;\n  }\n\n  const flags = descriptor[9] ?? 0;\n  const programSegmentationFlag = (flags & 0x80) !== 0;\n  const segmentationDurationFlag = (flags & 0x40) !== 0;\n  let offset = 10;\n\n  if (!programSegmentationFlag) {\n    const componentCount = descriptor[offset] ?? 0;\n    offset += 1 + componentCount * 6;\n    if (offset > descriptor.length) {\n      return undefined;\n    }\n  }\n\n  let durationSeconds: number | undefined = undefined;\n  if (segmentationDurationFlag) {\n    if (offset + 5 > descriptor.length) {\n      return undefined;\n    }\n    const durationTicks =\n      ((descriptor[offset] ?? 0) * 0x100000000) +\n      ((descriptor[offset + 1] ?? 0) * 0x1000000) +\n      ((descriptor[offset + 2] ?? 0) << 16) +\n      ((descriptor[offset + 3] ?? 0) << 8) +\n      (descriptor[offset + 4] ?? 0);\n    durationSeconds = durationTicks / 90000;\n    offset += 5;\n  }\n\n  if (offset + 2 > descriptor.length) {\n    return undefined;\n  }\n  offset += 1;\n  const segmentationUpidLength = descriptor[offset] ?? 0;\n  offset += 1 + segmentationUpidLength;\n  if (offset >= descriptor.length) {\n    return undefined;\n  }\n\n  const segmentationTypeId = descriptor[offset] ?? 0;\n  const markerType = markerTypeFromSegmentationTypeId(segmentationTypeId);\n  if (!markerType) {\n    return undefined;\n  }\n\n  return {\n    type: markerType,\n    ...(durationSeconds !== undefined ? { durationSeconds } : {}),\n    segmentationEventId,\n  };\n}\n\nfunction parseScte35SegmentationDescriptors(\n  data: Uint8Array,\n  offset: number\n):\n  | {\n      type: Scte35Marker[\"type\"];\n      durationSeconds?: number;\n      segmentationEventId?: number;\n    }\n  | undefined {\n  if (offset + 2 > data.length) {\n    return undefined;\n  }\n\n  const descriptorLoopLength =\n    ((data[offset] ?? 0) << 8) | (data[offset + 1] ?? 0);\n  let descriptorOffset = offset + 2;\n  const descriptorEnd = Math.min(\n    data.length,\n    descriptorOffset + descriptorLoopLength\n  );\n\n  while (descriptorOffset + 2 <= descriptorEnd) {\n    const descriptorTag = data[descriptorOffset] ?? 0;\n    const descriptorLength = data[descriptorOffset + 1] ?? 0;\n    const descriptorDataStart = descriptorOffset + 2;\n    const descriptorDataEnd = descriptorDataStart + descriptorLength;\n    if (descriptorDataEnd > descriptorEnd) {\n      return undefined;\n    }\n\n    if (descriptorTag === 0x02) {\n      const descriptorMarker = parseScte35SegmentationDescriptor(\n        data.subarray(descriptorDataStart, descriptorDataEnd)\n      );\n      if (descriptorMarker) {\n        return descriptorMarker;\n      }\n    }\n\n    descriptorOffset = descriptorDataEnd;\n  }\n\n  return undefined;\n}\n\nexport function parseScte35Binary(data: Uint8Array): Scte35Marker | undefined {\n  const r = new BitReader(data);\n  const tableId = r.readBits(8);\n  if (tableId !== 0xfc) return undefined;\n  r.readBits(1);\n  r.readBits(1);\n  r.readBits(2);\n  const sectionLength = r.readBits(12);\n  if (sectionLength <= 0 || data.length < 3 + sectionLength) {\n    return undefined;\n  }\n  r.readBits(8);\n  r.readBits(1);\n  r.readBits(6);\n  const ptsAdjHigh = r.readBits(1);\n  const ptsAdjLow = r.readBits(32);\n  const ptsAdjustmentTicks = ptsAdjHigh * 0x100000000 + ptsAdjLow;\n  r.readBits(8);\n  r.readBits(12);\n  const spliceCommandLength = r.readBits(12);\n  const spliceCommandType = r.readBits(8);\n\n  let markerType: Scte35Marker[\"type\"] | undefined;\n  let durationSeconds: number | undefined = undefined;\n  let ptsSeconds: number | undefined = undefined;\n  let spliceEventId: number | undefined = undefined;\n  const commandBodyStart = r.bytePosition;\n\n  if (spliceCommandType === 5) {\n    spliceEventId = r.readBits(32);\n    const cancel = r.readBits(1) === 1;\n    r.readBits(7);\n    if (cancel) return undefined;\n    const outOfNetwork = r.readBits(1) === 1;\n    const programSpliceFlag = r.readBits(1) === 1;\n    const durationFlag = r.readBits(1) === 1;\n    const spliceImmediateFlag = r.readBits(1) === 1;\n    r.readBits(4);\n    markerType = outOfNetwork ? \"start\" : \"end\";\n\n    if (programSpliceFlag && !spliceImmediateFlag) {\n      ptsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n    } else if (!programSpliceFlag) {\n      const componentCount = r.readBits(8);\n      for (let i = 0; i < componentCount; i++) {\n        r.readBits(8);\n        if (!spliceImmediateFlag) {\n          const componentPtsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n          if (ptsSeconds === undefined) {\n            ptsSeconds = componentPtsSeconds;\n          }\n        }\n      }\n    }\n\n    if (durationFlag) {\n      r.readBits(6);\n      r.readBits(1);\n      const high = r.readBits(1);\n      const low = r.readBits(32);\n      const durationTicks = high * 0x100000000 + low;\n      durationSeconds = durationTicks / 90000;\n    }\n    r.readBits(16);\n    r.readBits(8);\n    r.readBits(8);\n  } else if (spliceCommandType === 6) {\n    ptsSeconds = readSpliceTime(r, ptsAdjustmentTicks);\n  } else {\n    return undefined;\n  }\n\n  const expectedDescriptorOffset =\n    spliceCommandLength === 0x0fff\n      ? r.bytePosition\n      : commandBodyStart + spliceCommandLength;\n  const descriptorMarker = parseScte35SegmentationDescriptors(\n    data,\n    expectedDescriptorOffset\n  );\n\n  if (descriptorMarker) {\n    markerType = descriptorMarker.type;\n    if (durationSeconds === undefined) {\n      durationSeconds = descriptorMarker.durationSeconds;\n    }\n  }\n\n  if (!markerType) {\n    return undefined;\n  }\n\n  const marker: Scte35Marker = {\n    type: markerType,\n    ...(ptsSeconds !== undefined ? { ptsSeconds } : {}),\n    ...(durationSeconds !== undefined ? { durationSeconds } : {}),\n    raw: {\n      splice_command_type: spliceCommandType,\n      ...(spliceEventId !== undefined ? { splice_event_id: spliceEventId } : {}),\n      ...(descriptorMarker?.segmentationEventId !== undefined\n        ? { segmentation_event_id: descriptorMarker.segmentationEventId }\n        : {}),\n    },\n  } as Scte35Marker;\n  return marker;\n}\n","import type { Scte35Marker } from \"../types\";\nimport type {\n  NormalizedScte35Cue,\n  Scte35CueContext,\n  Scte35CueSource,\n  Scte35CueReadiness,\n} from \"./playerTypes\";\nimport { getFragmentStartSeconds } from \"./Scte35Parser\";\n\nexport interface Scte35CueManagerCallbacks {\n  onEarlyStartCue(marker: Scte35Marker, fragmentSn: number | undefined, cueKey: string): void;\n  onPlaybackCue(marker: Scte35Marker, cueKey?: string): void;\n  isInAdBreak(): boolean;\n}\n\nexport class Scte35CueManager {\n  private readonly pendingScte35Cues: Map<string, NormalizedScte35Cue> = new Map();\n  private readonly recentScte35CueKeys: Map<string, number> = new Map();\n  private readonly recentScte35CueLimit: number = 200;\n  private pendingScte35CueKeyValue: string | undefined;\n  private activeScte35BreakKeyValue: string | undefined;\n  private scheduledScte35BreakKeyValue: string | undefined;\n\n  readonly tsScte35Pids: Set<number> = new Set();\n  readonly pmtPids: Set<number> = new Set();\n  readonly processedTsScte35Sections: Set<string> = new Set();\n\n  private debug: boolean;\n  private callbacks: Scte35CueManagerCallbacks;\n\n  constructor(debug: boolean, callbacks: Scte35CueManagerCallbacks) {\n    this.debug = debug;\n    this.callbacks = callbacks;\n  }\n\n  get pendingScte35CueKey(): string | undefined {\n    return this.pendingScte35CueKeyValue;\n  }\n  set pendingScte35CueKey(value: string | undefined) {\n    this.pendingScte35CueKeyValue = value;\n  }\n\n  get activeScte35BreakKey(): string | undefined {\n    return this.activeScte35BreakKeyValue;\n  }\n  set activeScte35BreakKey(value: string | undefined) {\n    this.activeScte35BreakKeyValue = value;\n  }\n\n  get scheduledScte35BreakKey(): string | undefined {\n    return this.scheduledScte35BreakKeyValue;\n  }\n  set scheduledScte35BreakKey(value: string | undefined) {\n    this.scheduledScte35BreakKeyValue = value;\n  }\n\n  createScte35CueContext(\n    source: Scte35CueSource,\n    readiness: Scte35CueReadiness,\n    frag?: any\n  ): Scte35CueContext {\n    const context: Scte35CueContext = { source, readiness };\n    if (typeof frag?.sn === \"number\") {\n      context.fragmentSn = frag.sn;\n    }\n    const fragmentStartSec = getFragmentStartSeconds(frag);\n    if (fragmentStartSec !== undefined) {\n      context.fragmentStartSeconds = fragmentStartSec;\n    }\n    return context;\n  }\n\n  onScte35Cue(marker: Scte35Marker, context: Scte35CueContext): void {\n    const cue = this.createScte35Cue(marker, context);\n    const pendingKey = this.getPendingScte35CueKey(cue);\n\n    if (context.readiness === \"early\") {\n      this.pendingScte35Cues.set(pendingKey, cue);\n      this.trimRecentScte35CueMaps();\n\n      if (marker.type === \"start\") {\n        this.callbacks.onEarlyStartCue(marker, context.fragmentSn, cue.key);\n      }\n      return;\n    }\n\n    if (marker.type === \"end\" && !this.shouldAcceptScte35EndCue(cue)) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Ignoring SCTE-35 end cue\", {\n          key: cue.key,\n          activeScte35BreakKey: this.activeScte35BreakKeyValue,\n          inAdBreak: this.callbacks.isInAdBreak(),\n          source: cue.source,\n        });\n      }\n      return;\n    }\n\n    if (marker.type === \"start\" && this.hasRecentlyHandledScte35Cue(cue)) {\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Ignoring duplicate SCTE-35 start cue\", {\n          key: cue.key,\n          source: cue.source,\n        });\n      }\n      return;\n    }\n\n    this.pendingScte35Cues.delete(pendingKey);\n    this.markScte35CueHandled(cue);\n    this.callbacks.onPlaybackCue(marker, cue.key);\n  }\n\n  activatePendingScte35CuesForFragment(frag: any): void {\n    const fragmentSn = typeof frag?.sn === \"number\" ? frag.sn : undefined;\n    if (fragmentSn === undefined) {\n      return;\n    }\n\n    const matchingCues = Array.from(this.pendingScte35Cues.entries()).filter(\n      ([, cue]) => cue.fragmentSn === fragmentSn\n    );\n\n    matchingCues.forEach(([pendingKey, cue]) => {\n      this.pendingScte35Cues.delete(pendingKey);\n      const context: Scte35CueContext = {\n        source: cue.source,\n        readiness: \"playback\",\n      };\n      context.fragmentSn = fragmentSn;\n      const fragmentStartSec =\n        cue.fragmentStartSeconds ?? getFragmentStartSeconds(frag);\n      if (fragmentStartSec !== undefined) {\n        context.fragmentStartSeconds = fragmentStartSec;\n      }\n      this.onScte35Cue(cue.marker, context);\n    });\n  }\n\n  private createScte35Cue(\n    marker: Scte35Marker,\n    context: Scte35CueContext\n  ): NormalizedScte35Cue {\n    const cue: NormalizedScte35Cue = {\n      marker,\n      source: context.source,\n      readiness: context.readiness,\n      key: this.getScte35CueKey(marker, context),\n    };\n    if (context.fragmentSn !== undefined) {\n      cue.fragmentSn = context.fragmentSn;\n    }\n    if (context.fragmentStartSeconds !== undefined) {\n      cue.fragmentStartSeconds = context.fragmentStartSeconds;\n    }\n    return cue;\n  }\n\n  private getScte35CueKey(\n    marker: Scte35Marker,\n    context: Scte35CueContext\n  ): string {\n    const raw = this.getScte35MarkerRaw(marker);\n    const spliceEventId = this.toIdentityString(raw?.splice_event_id);\n    if (spliceEventId) {\n      return `splice:${spliceEventId}`;\n    }\n\n    const segmentationEventId = this.toIdentityString(raw?.segmentation_event_id);\n    if (segmentationEventId) {\n      return `segmentation:${segmentationEventId}`;\n    }\n\n    const daterangeId = this.toIdentityString(raw?.attrs?.ID);\n    if (daterangeId) {\n      return `daterange:${daterangeId}`;\n    }\n\n    const scteValue =\n      this.toIdentityString(raw?.attrs?.[\"SCTE35-OUT\"]) ||\n      this.toIdentityString(raw?.attrs?.[\"SCTE35-IN\"]);\n    if (scteValue) {\n      return `daterange-scte:${scteValue}`;\n    }\n\n    if (typeof marker.ptsSeconds === \"number\" && Number.isFinite(marker.ptsSeconds)) {\n      return `pts:${Math.round(marker.ptsSeconds * 2) / 2}`;\n    }\n\n    if (context.fragmentSn !== undefined) {\n      return `fragment:${context.fragmentSn}`;\n    }\n\n    return `${context.source}:wallclock:${Math.floor(Date.now() / 1000)}`;\n  }\n\n  private getPendingScte35CueKey(cue: NormalizedScte35Cue): string {\n    return `${cue.marker.type}:${cue.key}:${\n      cue.fragmentSn !== undefined ? cue.fragmentSn : \"unknown\"\n    }`;\n  }\n\n  private getScte35MarkerRaw(marker: Scte35Marker): any {\n    return typeof marker.raw === \"object\" && marker.raw !== null\n      ? (marker.raw as any)\n      : {};\n  }\n\n  private toIdentityString(value: unknown): string | undefined {\n    if (typeof value === \"number\" && Number.isFinite(value)) {\n      return String(value);\n    }\n    if (typeof value === \"string\" && value.trim().length > 0) {\n      return value.trim();\n    }\n    return undefined;\n  }\n\n  isStrongScte35CueKey(key: string | undefined): boolean {\n    return !!(\n      key &&\n      (key.startsWith(\"splice:\") ||\n        key.startsWith(\"segmentation:\") ||\n        key.startsWith(\"daterange:\") ||\n        key.startsWith(\"daterange-scte:\"))\n    );\n  }\n\n  private hasRecentlyHandledScte35Cue(cue: NormalizedScte35Cue): boolean {\n    if (\n      this.activeScte35BreakKeyValue === cue.key ||\n      this.scheduledScte35BreakKeyValue === cue.key\n    ) {\n      return true;\n    }\n\n    const recentKey = `${cue.marker.type}:${cue.key}`;\n    return this.recentScte35CueKeys.has(recentKey);\n  }\n\n  private markScte35CueHandled(cue: NormalizedScte35Cue): void {\n    this.recentScte35CueKeys.set(`${cue.marker.type}:${cue.key}`, Date.now());\n    this.trimRecentScte35CueMaps();\n  }\n\n  private trimRecentScte35CueMaps(): void {\n    while (this.recentScte35CueKeys.size > this.recentScte35CueLimit) {\n      const firstKey = this.recentScte35CueKeys.keys().next().value;\n      if (!firstKey) {\n        break;\n      }\n      this.recentScte35CueKeys.delete(firstKey);\n    }\n\n    while (this.pendingScte35Cues.size > this.recentScte35CueLimit) {\n      const firstKey = this.pendingScte35Cues.keys().next().value;\n      if (!firstKey) {\n        break;\n      }\n      this.pendingScte35Cues.delete(firstKey);\n    }\n  }\n\n  private shouldAcceptScte35EndCue(cue: NormalizedScte35Cue): boolean {\n    if (!this.callbacks.isInAdBreak()) {\n      return false;\n    }\n\n    if (\n      this.isStrongScte35CueKey(this.activeScte35BreakKeyValue) &&\n      this.isStrongScte35CueKey(cue.key) &&\n      this.activeScte35BreakKeyValue !== cue.key\n    ) {\n      return false;\n    }\n\n    return true;\n  }\n}\n","import type {\n  StormcloudVideoPlayerConfig,\n  AdBreak,\n  StormcloudApiResponse,\n  AdController,\n} from \"../types\";\nimport type { PalNonceManager } from \"../sdk/pal\";\nimport { applyVastMacros, generateCorrelator, normalizeVastTagUrl } from \"../utils/vastMacros\";\nimport type { VastConsentSignals } from \"../utils/vastMacros\";\nimport { resolveVastEnvironmentSignals } from \"../utils/vastEnvironmentSignals\";\nimport { toDevSafeUrl } from \"../utils/devUrl\";\nimport {\n  buildAnalyticsContext,\n  sendHeartbeat,\n  sendInitialTracking,\n} from \"../utils/tracking\";\nimport { applyMQTTConfig } from \"../utils/mqttConfig\";\n\nexport class AdConfigManager {\n  vmapBreaks: AdBreak[] = [];\n  consumedVmapBreakIds: Set<string> = new Set();\n  apiVastTagUrl: string | undefined;\n  apiNumberAds: number | undefined;\n  readonly streamCorrelator: string = generateCorrelator();\n  readonly viewCorrelator: string = generateCorrelator();\n  consentSignals: VastConsentSignals = {};\n  podCounter: number = 0;\n  podAssignedByPrefetch: boolean = false;\n\n  private lastHeartbeatTime: number = 0;\n  private heartbeatInterval: number | undefined;\n\n  private config: StormcloudVideoPlayerConfig;\n  private video: HTMLVideoElement;\n\n  constructor(config: StormcloudVideoPlayerConfig, video: HTMLVideoElement) {\n    this.config = config;\n    this.video = video;\n  }\n\n  get debug(): boolean {\n    return !!this.config.debugAdTiming;\n  }\n\n  isVmapEnabled(): boolean {\n    return !!(this.config.isVmap && this.config.vmapUrl?.trim());\n  }\n\n  async fetchAdConfiguration(): Promise<void> {\n    if (this.isVmapEnabled()) {\n      await this.fetchAndParseVmap(this.config.vmapUrl!);\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] VMAP mode enabled\");\n      }\n      return;\n    }\n\n    const vastMode = this.config.vastMode || \"default\";\n\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] VAST mode:\", vastMode);\n    }\n\n    if (vastMode === \"adstorm\") {\n      if (!this.config.licenseKey) {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] AdStorm mode requires a license key\"\n          );\n        }\n        return;\n      }\n\n      const vastEndpoint = `https://adstorm.co/api-adstorm-dev/adstorm/vast/${this.config.licenseKey}`;\n      this.apiVastTagUrl = vastEndpoint;\n\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Using AdStorm VAST endpoint (adstorm mode):\",\n          vastEndpoint\n        );\n      }\n      return;\n    }\n\n    if (this.config.vastTagUrl) {\n      this.apiVastTagUrl = normalizeVastTagUrl(this.config.vastTagUrl);\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Using custom VAST tag URL:\",\n          this.apiVastTagUrl\n        );\n      }\n      return;\n    }\n\n    const apiUrl = \"https://adstorm.co/api-adstorm-dev/adstorm/ads/web\";\n\n    if (this.debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Fetching ad configuration from:\",\n        apiUrl\n      );\n    }\n\n    const headers: Record<string, string> = {};\n    if (this.config.licenseKey) {\n      headers[\"Authorization\"] = `Bearer ${this.config.licenseKey}`;\n    }\n\n    const response = await fetch(apiUrl, { headers });\n    if (!response.ok) {\n      if (this.debug) {\n        console.warn(\n          `[StormcloudVideoPlayer] Failed to fetch ad configuration: ${response.status}`\n        );\n      }\n      return;\n    }\n\n    const data: StormcloudApiResponse = await response.json();\n\n    this.applyMqttConfigFromResponse(data);\n\n    const imaPayload = data.response?.ima?.[\"publisherdesk.ima\"]?.payload;\n    if (imaPayload) {\n      let decodedPayload = imaPayload;\n      try {\n        decodedPayload = decodeURIComponent(imaPayload);\n      } catch {\n        console.warn(\"[StormcloudVideoPlayer] imaPayload was not URI-encoded; using as-is:\", imaPayload);\n      }\n      console.log(\"[StormcloudVideoPlayer] Raw VAST tag URL (from API):\", decodedPayload);\n      this.apiVastTagUrl = normalizeVastTagUrl(decodedPayload);\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Normalized VAST tag URL:\",\n          this.apiVastTagUrl\n        );\n      }\n    } else {\n      if (this.debug) {\n        console.warn(\n          \"[StormcloudVideoPlayer] No VAST tag URL found in /ads/web response\"\n        );\n      }\n    }\n\n    const numberAds = data.response?.options?.vast?.cue_tones?.number_ads;\n    if (numberAds != null && numberAds > 0) {\n      this.apiNumberAds = numberAds;\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Number of ads per break from API:\",\n          this.apiNumberAds\n        );\n      }\n    }\n  }\n\n  private applyMqttConfigFromResponse(data: StormcloudApiResponse): void {\n    const mqttConfig = data.response?.mqtt_config;\n    if (!mqttConfig || typeof mqttConfig !== \"object\") {\n      return;\n    }\n\n    applyMQTTConfig(mqttConfig);\n\n    if (this.debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Applied MQTT config from /ads/web:\",\n        mqttConfig\n      );\n    }\n  }\n\n  private async fetchAndParseVmap(vmapUrl: string): Promise<void> {\n    if (!vmapUrl.trim()) {\n      return;\n    }\n\n    try {\n      const response = await fetch(vmapUrl);\n      if (!response.ok) {\n        throw new Error(`Failed to fetch VMAP (${response.status})`);\n      }\n\n      const vmapXml = await response.text();\n      this.vmapBreaks = this.parseVmapToBreaks(vmapXml);\n      this.consumedVmapBreakIds.clear();\n\n      if (this.debug) {\n        console.log(\n          `[StormcloudVideoPlayer] Loaded ${this.vmapBreaks.length} VMAP ad break(s) from:`,\n          vmapUrl\n        );\n      }\n    } catch (error) {\n      this.vmapBreaks = [];\n      this.consumedVmapBreakIds.clear();\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to load VMAP:\", error);\n      }\n    }\n  }\n\n  private parseVmapToBreaks(vmapXml: string): AdBreak[] {\n    if (typeof DOMParser === \"undefined\") {\n      return [];\n    }\n\n    const doc = new DOMParser().parseFromString(vmapXml, \"application/xml\");\n    if (doc.querySelector(\"parsererror\")) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Invalid VMAP XML received\");\n      }\n      return [];\n    }\n\n    const VMAP_NS = \"http://www.iab.net/videosuite/vmap\";\n    let adBreakNodes = Array.from(doc.getElementsByTagNameNS(VMAP_NS, \"AdBreak\"));\n    if (adBreakNodes.length === 0) {\n      adBreakNodes = Array.from(\n        doc.querySelectorAll(\"AdBreak, vmap\\\\:AdBreak\")\n      );\n    }\n    if (adBreakNodes.length === 0) {\n      adBreakNodes = Array.from(doc.getElementsByTagName(\"*\")).filter(\n        (el) => el.localName === \"AdBreak\"\n      );\n    }\n    const parsed: AdBreak[] = [];\n\n    adBreakNodes.forEach((node, index) => {\n      const timeOffsetRaw = (node.getAttribute(\"timeOffset\") || \"\").trim();\n      const startTimeMs = this.parseVmapTimeOffsetToMs(timeOffsetRaw);\n      if (startTimeMs == null) {\n        return;\n      }\n\n      let adTagNode = node.getElementsByTagNameNS(VMAP_NS, \"AdTagURI\")[0];\n      if (!adTagNode) {\n        adTagNode =\n          (node.querySelector(\"AdTagURI, vmap\\\\:AdTagURI\") as Element | null) ??\n          undefined;\n      }\n      const adTagUrl = (adTagNode?.textContent || \"\").trim();\n      if (!adTagUrl) {\n        return;\n      }\n\n      const breakId =\n        node.getAttribute(\"breakId\") ||\n        `vmap-break-${index}-${timeOffsetRaw || \"unknown\"}`;\n      parsed.push({\n        id: breakId,\n        startTimeMs,\n        vastTagUrl: adTagUrl,\n      });\n    });\n\n    parsed.sort((a, b) => {\n      const aStart = a.startTimeMs < 0 ? Number.MAX_SAFE_INTEGER : a.startTimeMs;\n      const bStart = b.startTimeMs < 0 ? Number.MAX_SAFE_INTEGER : b.startTimeMs;\n      return aStart - bStart;\n    });\n\n    return parsed;\n  }\n\n  private parseVmapTimeOffsetToMs(timeOffset: string): number | undefined {\n    if (!timeOffset) {\n      return undefined;\n    }\n\n    const normalized = timeOffset.trim().toLowerCase();\n    if (normalized === \"start\") {\n      return 0;\n    }\n\n    if (normalized === \"end\") {\n      return -1;\n    }\n\n    const hms = timeOffset.match(\n      /^(\\d{1,2}):(\\d{2}):(\\d{2})(?:\\.(\\d{1,3}))?$/\n    );\n    if (hms) {\n      const [, hh, mm, ss, ms = \"0\"] = hms;\n      const hours = Number(hh);\n      const minutes = Number(mm);\n      const seconds = Number(ss);\n      const millis = Number(ms.padEnd(3, \"0\").slice(0, 3));\n      return ((hours * 3600 + minutes * 60 + seconds) * 1000) + millis;\n    }\n\n    const percent = timeOffset.match(/^(\\d+(?:\\.\\d+)?)%$/);\n    if (percent) {\n      const ratio = Number(percent[1]) / 100;\n      const durationSec = this.video.duration;\n      if (Number.isFinite(durationSec) && durationSec > 0) {\n        return Math.floor(durationSec * 1000 * ratio);\n      }\n      return undefined;\n    }\n\n    return undefined;\n  }\n\n  getAdBreakKey(adBreak: AdBreak): string {\n    if (adBreak.id) {\n      return adBreak.id;\n    }\n    return `${adBreak.startTimeMs}-${adBreak.vastTagUrl || \"\"}`;\n  }\n\n  resolveBreakStartMs(adBreak: AdBreak): number | undefined {\n    if (adBreak.startTimeMs >= 0) {\n      return adBreak.startTimeMs;\n    }\n\n    if (adBreak.startTimeMs === -1) {\n      const durationSec = this.video.duration;\n      if (Number.isFinite(durationSec) && durationSec > 0) {\n        return Math.floor(durationSec * 1000);\n      }\n    }\n\n    return undefined;\n  }\n\n  findCurrentOrNextBreak(nowMs: number): AdBreak | undefined {\n    const schedule: AdBreak[] = this.vmapBreaks;\n    let candidate: AdBreak | undefined;\n    const tol = this.config.driftToleranceMs ?? 1000;\n    for (const b of schedule) {\n      if (this.consumedVmapBreakIds.has(this.getAdBreakKey(b))) {\n        continue;\n      }\n      const breakStartMs = this.resolveBreakStartMs(b);\n      if (breakStartMs == null) {\n        continue;\n      }\n      if (\n        breakStartMs <= nowMs + tol &&\n        (candidate == null ||\n          breakStartMs > (this.resolveBreakStartMs(candidate) ?? 0))\n      ) {\n        candidate = b;\n      }\n    }\n    return candidate;\n  }\n\n  findBreakForTime(nowMs: number): AdBreak | undefined {\n    const schedule: AdBreak[] = this.vmapBreaks;\n    for (const b of schedule) {\n      if (this.consumedVmapBreakIds.has(this.getAdBreakKey(b))) {\n        continue;\n      }\n      const breakStartMs = this.resolveBreakStartMs(b);\n      if (breakStartMs == null) {\n        continue;\n      }\n\n      if (b.durationMs) {\n        const end = breakStartMs + b.durationMs;\n        if (nowMs >= breakStartMs && nowMs < end) {\n          return b;\n        }\n        continue;\n      }\n\n      if (nowMs >= breakStartMs) {\n        return b;\n      }\n    }\n    return undefined;\n  }\n\n  selectVastTagsForBreak(b?: AdBreak): string[] | undefined {\n    if (!b || !b.vastTagUrl) return undefined;\n    if (b.vastTagUrl.includes(\",\")) {\n      return b.vastTagUrl\n        .split(\",\")\n        .map((s) => s.trim())\n        .filter((s) => s.length > 0);\n    }\n    return [b.vastTagUrl];\n  }\n\n  beginNewAdPod(): void {\n    this.podCounter++;\n  }\n\n  private readonly defaultPodMaxAds: number = 6;\n  private readonly defaultPodMaxDurationMs: number = 120000;\n\n  resolvePodParams(breakDurationMs?: number): {\n    maxAds: number;\n    minDurationMs: number;\n    maxDurationMs: number;\n  } {\n    const maxDurationMs =\n      breakDurationMs != null && breakDurationMs > 0\n        ? breakDurationMs\n        : this.config.podMaxDurationMs != null && this.config.podMaxDurationMs > 0\n          ? this.config.podMaxDurationMs\n          : this.defaultPodMaxDurationMs;\n\n    const maxAds =\n      this.config.podMaxAds && this.config.podMaxAds > 0\n        ? this.config.podMaxAds\n        : this.apiNumberAds && this.apiNumberAds > 0\n          ? this.apiNumberAds\n          : this.defaultPodMaxAds;\n\n    const minDurationMs =\n      this.config.podExactDuration && maxDurationMs != null ? maxDurationMs : 0;\n\n    return { maxAds, minDurationMs, maxDurationMs };\n  }\n\n  generatePodVastUrl(\n    baseUrl: string,\n    podParams: { maxAds: number; minDurationMs: number; maxDurationMs: number },\n    adPlayer: AdController,\n    palNonce: PalNonceManager,\n    inAdBreak: boolean\n  ): string {\n    const adWillPlayMuted = inAdBreak\n      ? adPlayer.getOriginalMutedState()\n      : this.video.muted;\n    const envSignals = resolveVastEnvironmentSignals(!!this.config.ctvAdRequest);\n\n    const urlWithMacros = applyVastMacros(baseUrl, {\n      correlator: this.viewCorrelator,\n      streamCorrelator: this.streamCorrelator,\n      pod: this.podCounter > 0 ? this.podCounter : undefined,\n      podMaxAds: podParams.maxAds,\n      podMinDurationMs: podParams.minDurationMs,\n      podMaxDurationMs: podParams.maxDurationMs,\n      isCtv: envSignals.isCtv,\n      contentUrl: envSignals.contentUrl,\n      pageUrl:\n        !envSignals.isCtv && typeof window !== \"undefined\"\n          ? toDevSafeUrl(window.location.href)\n          : undefined,\n      adWillPlayMuted,\n      adWillAutoPlay: !!this.config.autoplay,\n      appId: envSignals.appId,\n      appName: envSignals.appName,\n      sessionId: envSignals.sessionId,\n      deviceId: envSignals.deviceId,\n      deviceIdType: envSignals.deviceIdType,\n      limitAdTracking: envSignals.limitAdTracking,\n      deviceTypeHint: envSignals.deviceTypeHint,\n      adTest: this.config.adTest,\n      consent: this.consentSignals,\n    });\n\n    const finalUrl = palNonce.injectNonce(urlWithMacros);\n    console.log(\n      `[StormcloudVideoPlayer] Resolved optimized-pod request URL (pod=${this.podCounter}, pmad=${podParams.maxAds}, pmnd=${podParams.minDurationMs}, pmxd=${podParams.maxDurationMs ?? \"?\"}):`,\n      finalUrl\n    );\n    return finalUrl;\n  }\n\n  // --- Tracking ---\n\n  initializeTracking(): void {\n    sendInitialTracking(this.config.licenseKey, buildAnalyticsContext(this.config))\n      .then(() => {\n        this.heartbeatInterval = window.setInterval(() => {\n          this.sendHeartbeatIfNeeded();\n        }, 5000);\n      })\n      .catch((error) => {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] Failed to send initial tracking:\",\n            error\n          );\n        }\n        this.heartbeatInterval = window.setInterval(() => {\n          this.sendHeartbeatIfNeeded();\n        }, 5000);\n      });\n  }\n\n  private sendHeartbeatIfNeeded(): void {\n    const now = Date.now();\n    if (!this.lastHeartbeatTime || now - this.lastHeartbeatTime > 30000) {\n      this.lastHeartbeatTime = now;\n      sendHeartbeat(this.config.licenseKey, buildAnalyticsContext(this.config)).catch((error) => {\n        if (this.debug) {\n          console.warn(\n            \"[StormcloudVideoPlayer] Failed to send heartbeat:\",\n            error\n          );\n        }\n      });\n    }\n  }\n\n  destroyTracking(): void {\n    if (this.heartbeatInterval) {\n      clearInterval(this.heartbeatInterval);\n      this.heartbeatInterval = undefined;\n    }\n  }\n}\n","import type { AdController, StormcloudVideoPlayerConfig, Scte35Marker } from \"../types\";\n\nexport interface AdTimingCallbacks {\n  onAdStopTimerFired(): void;\n  onAdStartTimerFired(marker: Scte35Marker, cueKey: string | undefined): void;\n  onWatchdogTimeout(): void;\n  onFailsafeTimeout(): void;\n}\n\nexport class AdTimingService {\n  private adStopTimerId: number | undefined;\n  private adStartTimerId: number | undefined;\n  private adFailsafeTimerId: number | undefined;\n  private adRequestWatchdogId: number | undefined;\n  private adRequestWatchdogToken: number | null = null;\n  private adFailsafeToken: number | null = null;\n\n  ptsDriftEmaMs = 0;\n  expectedAdBreakDurationMs: number | undefined;\n  currentAdBreakStartWallClockMs: number | undefined;\n  scteAdBreakEndWallClockMs: number | undefined;\n  adBreakPlayedDurationMs: number = 0;\n  adBreakEpoch: number = 0;\n\n  adRequestTokenCounter = 0;\n  activeAdRequestToken: number | null = null;\n  currentAdIndex: number = 0;\n  totalAdsInBreak: number = 0;\n  totalAdRequestsInBreak: number = 0;\n  readonly maxTotalAdRequestsPerBreak: number = 10;\n  lastAdRequestTime: number = 0;\n  consecutiveFailures: number = 0;\n  readonly maxConsecutiveFailures: number = 5;\n  readonly minAdRequestIntervalMs: number = 3000;\n  readonly backoffBaseMs: number = 1000;\n  readonly maxBackoffMs: number = 15000;\n  private readonly defaultMinRemainingMsToStartAd: number = 4000;\n\n  failedVastUrls: Set<string> = new Set();\n  temporaryFailureUrls: Map<string, number> = new Map();\n  private readonly temporaryFailureCooldownMs: number = 30000;\n\n  private globalConsecutiveNoFills: number = 0;\n  private readonly globalNoFillThreshold: number = 3;\n  private globalNoFillCooldownUntil: number = 0;\n  private readonly globalNoFillBackoffBaseMs: number = 5000;\n  private readonly globalNoFillBackoffMaxMs: number = 60000;\n  private globalLastGamRequestTime: number = 0;\n  private readonly globalMinGamIntervalMs: number = 3000;\n\n  private config: StormcloudVideoPlayerConfig;\n  private video: HTMLVideoElement;\n  private callbacks: AdTimingCallbacks;\n\n  constructor(\n    config: StormcloudVideoPlayerConfig,\n    video: HTMLVideoElement,\n    callbacks: AdTimingCallbacks\n  ) {\n    this.config = config;\n    this.video = video;\n    this.callbacks = callbacks;\n  }\n\n  get debug(): boolean {\n    return !!this.config.debugAdTiming;\n  }\n\n  // --- Ad stop timer ---\n\n  scheduleAdStopCountdown(remainingMs: number): void {\n    this.clearAdStopTimer();\n    const ms = Math.max(0, Math.floor(remainingMs));\n    if (ms === 0) {\n      this.ensureAdStoppedByTimer();\n      return;\n    }\n    this.adStopTimerId = window.setTimeout(() => {\n      this.ensureAdStoppedByTimer();\n    }, ms) as unknown as number;\n  }\n\n  clearAdStopTimer(): void {\n    if (this.adStopTimerId != null) {\n      clearTimeout(this.adStopTimerId);\n      this.adStopTimerId = undefined;\n    }\n  }\n\n  private ensureAdStoppedByTimer(): void {\n    this.adStopTimerId = undefined;\n    this.callbacks.onAdStopTimerFired();\n  }\n\n  // --- Ad start timer ---\n\n  scheduleAdStartIn(\n    delayMs: number,\n    marker: Scte35Marker = { type: \"start\" } as Scte35Marker,\n    cueKey?: string\n  ): void {\n    this.clearAdStartTimer();\n    const ms = Math.max(0, Math.floor(delayMs));\n    if (ms === 0) {\n      this.callbacks.onAdStartTimerFired(marker, cueKey);\n      return;\n    }\n    this.adStartTimerId = window.setTimeout(() => {\n      this.callbacks.onAdStartTimerFired(marker, cueKey);\n    }, ms) as unknown as number;\n  }\n\n  clearAdStartTimer(): void {\n    if (this.adStartTimerId != null) {\n      clearTimeout(this.adStartTimerId);\n      this.adStartTimerId = undefined;\n    }\n  }\n\n  // --- PTS drift ---\n\n  updatePtsDrift(ptsSecondsSample: number): void {\n    const sampleMs = (this.video.currentTime - ptsSecondsSample) * 1000;\n    if (!Number.isFinite(sampleMs) || Math.abs(sampleMs) > 60000) return;\n    const alpha = 0.1;\n    this.ptsDriftEmaMs = this.ptsDriftEmaMs * (1 - alpha) + sampleMs * alpha;\n  }\n\n  resolveScteBreakStartWallClockMs(marker: Scte35Marker): number {\n    const nowWallClockMs = Date.now();\n    if (typeof marker.ptsSeconds !== \"number\") {\n      return nowWallClockMs;\n    }\n\n    const nowMs = this.video.currentTime * 1000;\n    const estimatedCurrentPtsMs = nowMs - this.ptsDriftEmaMs;\n    const deltaMs = marker.ptsSeconds * 1000 - estimatedCurrentPtsMs;\n    if (!Number.isFinite(deltaMs)) {\n      return nowWallClockMs;\n    }\n\n    return nowWallClockMs + Math.floor(deltaMs);\n  }\n\n  // --- Duration boundary ---\n\n  setAdBreakDurationBoundary(durationMs: number | undefined): void {\n    this.expectedAdBreakDurationMs = durationMs;\n    if (\n      durationMs != null &&\n      this.currentAdBreakStartWallClockMs != null\n    ) {\n      this.scteAdBreakEndWallClockMs =\n        this.currentAdBreakStartWallClockMs + durationMs;\n    } else {\n      this.scteAdBreakEndWallClockMs = undefined;\n    }\n  }\n\n  scheduleAdStopAtBreakBoundary(): void {\n    if (this.expectedAdBreakDurationMs == null) {\n      return;\n    }\n    this.scheduleAdStopCountdown(this.getWallClockRemainingAdMs());\n  }\n\n  // --- Duration budget ---\n\n  getWallClockRemainingAdMs(): number {\n    const endWallClockMs = this.getAdBreakEndWallClockMs();\n    if (endWallClockMs != null) {\n      return Math.max(0, endWallClockMs - Date.now());\n    }\n    return 0;\n  }\n\n  getAdBreakEndWallClockMs(): number | undefined {\n    if (this.scteAdBreakEndWallClockMs != null) {\n      return this.scteAdBreakEndWallClockMs;\n    }\n    if (\n      this.expectedAdBreakDurationMs == null ||\n      this.currentAdBreakStartWallClockMs == null\n    ) {\n      return undefined;\n    }\n    return this.currentAdBreakStartWallClockMs + this.expectedAdBreakDurationMs;\n  }\n\n  getDurationBudgetRemainingMs(): number {\n    if (this.expectedAdBreakDurationMs == null) {\n      return 0;\n    }\n    return Math.max(0, this.expectedAdBreakDurationMs - this.adBreakPlayedDurationMs);\n  }\n\n  getLoadedAdDurationMs(adController: AdController): number {\n    const durationSec = adController.getLoadedAdDuration?.();\n    if (durationSec == null || durationSec <= 0) {\n      return 0;\n    }\n    return Math.round(durationSec * 1000);\n  }\n\n  adFitsRemainingBudget(durationMs: number): boolean {\n    if (durationMs <= 0) {\n      return true;\n    }\n    return durationMs <= this.getDurationBudgetRemainingMs();\n  }\n\n  logAdDurationDecision(\n    accepted: boolean,\n    durationMs: number,\n    adController: AdController\n  ): void {\n    if (!this.debug) {\n      return;\n    }\n    const remainingBudget = this.getDurationBudgetRemainingMs();\n    const adId = adController.getLoadedAdId?.() ?? \"unknown\";\n    if (accepted) {\n      console.log(\n        `[AD-DURATION] Accepted ad id=${adId}, duration=${durationMs}ms, budget remaining after play=${Math.max(0, remainingBudget - durationMs)}ms`\n      );\n    } else {\n      console.log(\n        `[AD-DURATION] Rejected ad id=${adId}, duration=${durationMs}ms exceeds remaining budget=${remainingBudget}ms — requesting another ad`\n      );\n    }\n  }\n\n  recordPlayedAdDuration(adController: AdController): void {\n    const durationMs = this.getLoadedAdDurationMs(adController);\n    if (durationMs <= 0) {\n      return;\n    }\n    this.adBreakPlayedDurationMs += durationMs;\n    if (this.debug) {\n      console.log(\n        `[AD-DURATION] Played ${durationMs}ms — total played=${this.adBreakPlayedDurationMs}ms / ${this.expectedAdBreakDurationMs ?? \"?\"}ms`\n      );\n    }\n  }\n\n  ensureLoadedAdFitsBudget(adController: AdController): boolean {\n    const durationMs = this.getLoadedAdDurationMs(adController);\n    const fits = this.adFitsRemainingBudget(durationMs);\n    this.logAdDurationDecision(fits, durationMs, adController);\n    return fits;\n  }\n\n  rejectLoadedAdForDuration(adController: AdController): void {\n    try {\n      adController.destroy();\n    } catch {}\n  }\n\n  markAdStarted(): void {\n    this.currentAdIndex++;\n    this.totalAdsInBreak = this.currentAdIndex;\n    this.totalAdRequestsInBreak++;\n    this.lastAdRequestTime = Date.now();\n  }\n\n  notePodAdStarted(): void {\n    this.currentAdIndex++;\n    this.totalAdsInBreak = this.currentAdIndex;\n  }\n\n  getRemainingAdMs(): number {\n    const wallClockRemaining = this.getWallClockRemainingAdMs();\n    const budgetRemaining = this.getDurationBudgetRemainingMs();\n    if (this.expectedAdBreakDurationMs == null) {\n      return wallClockRemaining;\n    }\n    return Math.min(wallClockRemaining, budgetRemaining);\n  }\n\n  getMinRemainingMsToStartAd(): number {\n    const configured = this.config.minRemainingMsToStartAd;\n    if (typeof configured === \"number\" && configured >= 0) {\n      return configured;\n    }\n    return this.defaultMinRemainingMsToStartAd;\n  }\n\n  hasTimeToStartAnotherAd(): boolean {\n    const minRemaining = this.getMinRemainingMsToStartAd();\n    return (\n      this.getWallClockRemainingAdMs() > minRemaining &&\n      this.getDurationBudgetRemainingMs() > minRemaining\n    );\n  }\n\n  // --- Circuit breaker ---\n\n  isTemporaryAdError(error: Error): boolean {\n    const message = error?.message?.toLowerCase() || \"\";\n\n    if (message.includes(\"no ads available\") || message.includes(\"no fill\") || message.includes(\"nofill\")) {\n      return true;\n    }\n    if (message.includes(\"timeout\")) {\n      return true;\n    }\n    if (message.includes(\"rate limit\") || message.includes(\"too many requests\")) {\n      return true;\n    }\n    if (message.includes(\"ad playback error\")) {\n      return true;\n    }\n    return false;\n  }\n\n  isUrlInCooldown(vastTagUrl: string): boolean {\n    const failureTime = this.temporaryFailureUrls.get(vastTagUrl);\n    if (failureTime == null) {\n      return false;\n    }\n\n    const elapsed = Date.now() - failureTime;\n    if (elapsed >= this.temporaryFailureCooldownMs) {\n      this.temporaryFailureUrls.delete(vastTagUrl);\n      return false;\n    }\n\n    return true;\n  }\n\n  cleanupTemporaryFailures(): void {\n    const now = Date.now();\n    for (const [url, timestamp] of this.temporaryFailureUrls) {\n      if (now - timestamp >= this.temporaryFailureCooldownMs) {\n        this.temporaryFailureUrls.delete(url);\n      }\n    }\n  }\n\n  isGamInCooldown(): boolean {\n    return Date.now() < this.globalNoFillCooldownUntil;\n  }\n\n  recordGamNoFill(): void {\n    this.globalConsecutiveNoFills++;\n\n    if (this.globalConsecutiveNoFills >= this.globalNoFillThreshold) {\n      const exponent = this.globalConsecutiveNoFills - this.globalNoFillThreshold;\n      const backoff = Math.min(\n        this.globalNoFillBackoffBaseMs * Math.pow(2, exponent),\n        this.globalNoFillBackoffMaxMs\n      );\n      this.globalNoFillCooldownUntil = Date.now() + backoff;\n\n      if (this.debug) {\n        console.log(\n          `[CIRCUIT-BREAKER] GAM cooldown activated: ${backoff}ms (${this.globalConsecutiveNoFills} consecutive no-fills)`\n        );\n      }\n    }\n  }\n\n  resetGamNoFillCounter(): void {\n    if (this.globalConsecutiveNoFills > 0 && this.debug) {\n      console.log(\n        `[CIRCUIT-BREAKER] Resetting no-fill counter (was ${this.globalConsecutiveNoFills})`\n      );\n    }\n    this.globalConsecutiveNoFills = 0;\n    this.globalNoFillCooldownUntil = 0;\n  }\n\n  async enforceGlobalRateLimit(): Promise<void> {\n    const now = Date.now();\n    const elapsed = now - this.globalLastGamRequestTime;\n    if (elapsed < this.globalMinGamIntervalMs) {\n      const waitMs = this.globalMinGamIntervalMs - elapsed;\n      if (this.debug) {\n        console.log(`[RATE-LIMIT] Waiting ${waitMs}ms before next GAM request`);\n      }\n      await new Promise(resolve => setTimeout(resolve, waitMs));\n    }\n    this.globalLastGamRequestTime = Date.now();\n  }\n\n  // --- Watchdog ---\n\n  startAdRequestWatchdog(token: number): void {\n    this.clearAdRequestWatchdog();\n\n    const timeoutMs = this.config.adFailsafeTimeoutMs ?? 10000;\n    this.adRequestWatchdogToken = token;\n    this.adRequestWatchdogId = window.setTimeout(() => {\n      if (this.adRequestWatchdogToken !== token) {\n        return;\n      }\n\n      this.adRequestWatchdogId = undefined;\n      this.adRequestWatchdogToken = null;\n      if (this.activeAdRequestToken === token) {\n        this.activeAdRequestToken = null;\n      }\n\n      this.logAdState(\"ad_request_timeout\", { token, timeoutMs });\n      this.callbacks.onWatchdogTimeout();\n    }, timeoutMs) as unknown as number;\n\n    this.logAdState(\"ad_request_watchdog_started\", { token, timeoutMs });\n  }\n\n  clearAdRequestWatchdog(): void {\n    if (this.adRequestWatchdogId != null) {\n      clearTimeout(this.adRequestWatchdogId);\n      this.adRequestWatchdogId = undefined;\n    }\n\n    if (this.adRequestWatchdogToken != null) {\n      this.logAdState(\"ad_request_watchdog_cleared\", {\n        token: this.adRequestWatchdogToken,\n      });\n      this.adRequestWatchdogToken = null;\n    }\n  }\n\n  // --- Failsafe ---\n\n  startAdFailsafeTimer(token: number): void {\n    this.clearAdFailsafeTimer();\n\n    const failsafeMs = this.config.adFailsafeTimeoutMs ?? 10000;\n    this.adFailsafeToken = token;\n\n    this.adFailsafeTimerId = window.setTimeout(() => {\n      if (this.adFailsafeToken !== token) {\n        return;\n      }\n\n      this.adFailsafeTimerId = undefined;\n      this.adFailsafeToken = null;\n\n      if (this.activeAdRequestToken === token) {\n        this.activeAdRequestToken = null;\n      }\n\n      this.logAdState(\"ad_failsafe_triggered\", {\n        token,\n        failsafeMs,\n        videoPaused: this.video.paused,\n      });\n\n      this.callbacks.onFailsafeTimeout();\n    }, failsafeMs) as unknown as number;\n\n    this.logAdState(\"ad_failsafe_started\", { token, failsafeMs });\n  }\n\n  clearAdFailsafeTimer(): void {\n    if (this.adFailsafeTimerId != null) {\n      clearTimeout(this.adFailsafeTimerId);\n      this.logAdState(\"ad_failsafe_cleared\", { token: this.adFailsafeToken });\n      this.adFailsafeTimerId = undefined;\n    }\n\n    this.adFailsafeToken = null;\n  }\n\n  logAdState(event: string, extra: Record<string, unknown> = {}, adPlayer?: AdController, inAdBreak?: boolean, showAds?: boolean): void {\n    if (!this.debug) {\n      return;\n    }\n\n    console.log(\"[StormcloudVideoPlayer][AdState]\", {\n      event,\n      timestamp: new Date().toISOString(),\n      showAds: showAds ?? false,\n      adPlaying: adPlayer?.isAdPlaying() ?? false,\n      inAdBreak: inAdBreak ?? false,\n      activeAdRequestToken: this.activeAdRequestToken,\n      ...extra,\n    });\n  }\n\n  // --- Reset for ad break end ---\n\n  resetForBreakEnd(): void {\n    this.clearAdStopTimer();\n    this.clearAdStartTimer();\n    this.clearAdRequestWatchdog();\n    this.clearAdFailsafeTimer();\n    this.activeAdRequestToken = null;\n    this.expectedAdBreakDurationMs = undefined;\n    this.currentAdBreakStartWallClockMs = undefined;\n    this.scteAdBreakEndWallClockMs = undefined;\n    this.adBreakPlayedDurationMs = 0;\n    this.currentAdIndex = 0;\n    this.totalAdsInBreak = 0;\n    this.consecutiveFailures = 0;\n    this.globalConsecutiveNoFills = 0;\n    this.adBreakEpoch++;\n  }\n\n  destroy(): void {\n    this.clearAdStopTimer();\n    this.clearAdStartTimer();\n    this.clearAdFailsafeTimer();\n    this.clearAdRequestWatchdog();\n  }\n}\n","export class PlaceholderLayer {\n  private container: HTMLDivElement | undefined;\n  private debug: boolean;\n  private video: HTMLVideoElement;\n\n  constructor(video: HTMLVideoElement, debug: boolean) {\n    this.video = video;\n    this.debug = debug;\n  }\n\n  private ensureContainer(): void {\n    if (this.container) {\n      return;\n    }\n\n    const el = document.createElement(\"div\");\n    el.style.position = \"absolute\";\n    el.style.left = \"0\";\n    el.style.top = \"0\";\n    el.style.right = \"0\";\n    el.style.bottom = \"0\";\n    el.style.display = \"none\";\n    el.style.alignItems = \"center\";\n    el.style.justifyContent = \"center\";\n    el.style.pointerEvents = \"none\";\n    el.style.zIndex = \"5\";\n    el.style.backgroundColor = \"#000\";\n    el.style.transition = \"opacity 0.3s ease-in-out\";\n    el.style.opacity = \"0\";\n\n    if (!this.video.parentElement) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Video element has no parent for placeholder container\");\n      }\n      return;\n    }\n\n    this.video.parentElement.appendChild(el);\n    this.container = el;\n  }\n\n  show(): void {\n    this.ensureContainer();\n\n    if (!this.container) {\n      return;\n    }\n\n    if (!this.video.muted) {\n      this.video.muted = true;\n      if (this.debug) {\n        console.log(\"[StormcloudVideoPlayer] Muted video when showing placeholder\");\n      }\n    }\n\n    const wasHidden = this.container.style.display === \"none\" || this.container.style.opacity === \"0\";\n    if (wasHidden) {\n      this.container.style.transition = \"none\";\n    } else {\n      this.container.style.transition = \"opacity 0.3s ease-in-out\";\n    }\n\n    this.container.style.backgroundColor = \"#000\";\n    this.container.style.display = \"flex\";\n    this.container.offsetHeight;\n    this.container.style.opacity = \"1\";\n    this.container.style.pointerEvents = \"auto\";\n\n    if (wasHidden) {\n      requestAnimationFrame(() => {\n        if (this.container) {\n          this.container.style.transition = \"opacity 0.3s ease-in-out\";\n        }\n      });\n    }\n\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Showing placeholder layer (between content and ad layer)\");\n    }\n  }\n\n  hide(): void {\n    if (!this.container) {\n      return;\n    }\n\n    this.container.style.opacity = \"0\";\n    setTimeout(() => {\n      if (this.container) {\n        this.container.style.display = \"none\";\n        this.container.style.pointerEvents = \"none\";\n        this.container.style.backgroundColor = \"#000\";\n      }\n    }, 300);\n\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Hiding placeholder layer\");\n    }\n  }\n\n  destroy(): void {\n    if (this.container) {\n      if (this.container.parentElement) {\n        this.container.parentElement.removeChild(this.container);\n      }\n      this.container = undefined;\n    }\n  }\n}\n","import Hls from \"hls.js\";\nimport type {\n  StormcloudVideoPlayerConfig,\n  Scte35Marker,\n  Id3TagInfo,\n} from \"../types\";\nimport type { Scte35CueContext } from \"./playerTypes\";\nimport {\n  parseScte35FromId3,\n  parseScte35FromTsPackets,\n  normalizeFragmentPayload,\n  getFragmentStartSeconds,\n  parseCueOutDuration,\n  parseCueOutCont,\n  parseAttributeList,\n  toNumber,\n} from \"./Scte35Parser\";\nimport type { Scte35CueManager } from \"./Scte35CueManager\";\nimport type { AdTimingService } from \"./AdTimingService\";\n\nexport interface HlsEngineCallbacks {\n  onManifestParsed(isLive: boolean): Promise<void>;\n  onScte35Cue(marker: Scte35Marker, context: Scte35CueContext): void;\n  activatePendingCuesForFragment(frag: any): void;\n  onFatalDestroy(): void;\n  isInAdBreak(): boolean;\n  hasPendingAdBreak(): boolean;\n}\n\nexport class HlsEngine {\n  hls: Hls | undefined;\n  isLiveStream: boolean = false;\n  nativeHlsMode: boolean = false;\n  videoSrcProtection: string | null = null;\n  reloadingLiveStream: boolean = false;\n\n  private bufferedSegmentsCount: number = 0;\n  private shouldAutoplayAfterBuffering: boolean = false;\n  private hasInitialBufferCompleted: boolean = false;\n\n  private readonly config: StormcloudVideoPlayerConfig;\n  private readonly video: HTMLVideoElement;\n  private readonly cueManager: Scte35CueManager;\n  private readonly timing: AdTimingService;\n  private readonly callbacks: HlsEngineCallbacks;\n\n  constructor(\n    config: StormcloudVideoPlayerConfig,\n    video: HTMLVideoElement,\n    cueManager: Scte35CueManager,\n    timing: AdTimingService,\n    callbacks: HlsEngineCallbacks\n  ) {\n    this.config = config;\n    this.video = video;\n    this.cueManager = cueManager;\n    this.timing = timing;\n    this.callbacks = callbacks;\n  }\n\n  private get debug(): boolean {\n    return !!this.config.debugAdTiming;\n  }\n\n  shouldUseNativeHls(getStreamType: () => \"hls\" | \"other\"): boolean {\n    const streamType = getStreamType();\n    if (streamType === \"other\") {\n      return true;\n    }\n    const canNative = this.video.canPlayType(\"application/vnd.apple.mpegurl\");\n    return !!(this.config.allowNativeHls && canNative);\n  }\n\n  async setupNativeHls(): Promise<void> {\n    this.nativeHlsMode = true;\n    this.videoSrcProtection = this.config.src;\n    this.video.src = this.config.src;\n\n    this.isLiveStream = this.config.isLiveStream ?? (this.config.lowLatencyMode ?? false);\n\n    if (this.debug) {\n      const adBehavior = this.isLiveStream\n        ? \"live (main video continues muted during ads)\"\n        : \"vod (main video pauses during ads)\";\n      console.log(\n        \"[StormcloudVideoPlayer] Using native HLS playback:\",\n        {\n          isLive: this.isLiveStream,\n          allowNativeHls: this.config.allowNativeHls,\n          adBehavior,\n        }\n      );\n    }\n\n    if (this.config.autoplay) {\n      await this.video.play()?.catch(() => {});\n    }\n  }\n\n  setupHls(): void {\n    this.hls = new Hls({\n      enableWorker: true,\n      backBufferLength: 30,\n      liveDurationInfinity: true,\n      lowLatencyMode: !!this.config.lowLatencyMode,\n      maxLiveSyncPlaybackRate: this.config.lowLatencyMode ? 1.5 : 1.0,\n      ...(this.config.lowLatencyMode ? { liveSyncDuration: 2 } : {}),\n      maxBufferLength: 30,\n      maxMaxBufferLength: 600,\n      maxBufferSize: 60 * 1000 * 1000,\n      maxBufferHole: 0.5,\n      highBufferWatchdogPeriod: 2,\n      nudgeOffset: 0.1,\n      nudgeMaxRetry: 3,\n      startPosition: -1,\n    });\n\n    this.hls.on(Hls.Events.MEDIA_ATTACHED, () => {\n      this.hls?.loadSource(this.config.src);\n    });\n\n    this.hls.on(Hls.Events.MANIFEST_PARSED, async (_, _data: any) => {\n      this.isLiveStream =\n        this.config.isLiveStream ??\n        (this.hls?.levels?.some(\n          (level) =>\n            level?.details?.live === true || level?.details?.type === \"LIVE\"\n        ) ?? false);\n\n      await this.callbacks.onManifestParsed(this.isLiveStream);\n\n      this.bufferedSegmentsCount = 0;\n      this.hasInitialBufferCompleted = false;\n      this.shouldAutoplayAfterBuffering = !!this.config.autoplay;\n\n      const minSegments = this.config.minSegmentsBeforePlay ?? 2;\n\n      if (this.debug) {\n        console.log(\n          \"[StormcloudVideoPlayer] Waiting for\",\n          minSegments,\n          \"segments to buffer before playback\"\n        );\n      }\n\n      if (minSegments === 0 || !this.config.autoplay) {\n        this.hasInitialBufferCompleted = true;\n        if (this.config.autoplay) {\n          await this.video.play()?.catch(() => {});\n        }\n      }\n\n      this.reloadingLiveStream = false;\n    });\n\n    this.hls.on(Hls.Events.LEVEL_LOADED, (_evt, data: any) => {\n      if (this.callbacks.isInAdBreak() || this.callbacks.hasPendingAdBreak()) {\n        return;\n      }\n\n      const details = data?.details;\n      if (!details || !details.fragments || details.fragments.length === 0) {\n        return;\n      }\n\n      const fragmentsToScan = Math.min(5, details.fragments.length);\n\n      for (let i = 0; i < fragmentsToScan; i++) {\n        const frag = details.fragments[i];\n        const tagList: any[] | undefined = frag?.tagList;\n\n        if (!Array.isArray(tagList)) continue;\n\n        for (const entry of tagList) {\n          let tag = \"\";\n          let value = \"\";\n\n          if (Array.isArray(entry)) {\n            tag = String(entry[0] ?? \"\");\n            value = String(entry[1] ?? \"\");\n          } else if (typeof entry === \"string\") {\n            const idx = entry.indexOf(\":\");\n            if (idx >= 0) {\n              tag = entry.substring(0, idx);\n              value = entry.substring(idx + 1);\n            } else {\n              tag = entry;\n            }\n          }\n\n          if (!tag) continue;\n\n          if (tag.includes(\"EXT-X-CUE-OUT\") || tag.includes(\"EXT-X-DATERANGE\")) {\n            const attrs = tag.includes(\"EXT-X-DATERANGE\")\n              ? parseAttributeList(value)\n              : {};\n            const hasScteOut = tag.includes(\"EXT-X-CUE-OUT\") ||\n              \"SCTE35-OUT\" in attrs ||\n              attrs[\"SCTE35-OUT\"] !== undefined;\n\n            if (hasScteOut) {\n              const durationSeconds = parseCueOutDuration(value);\n              const marker: Scte35Marker = {\n                type: \"start\",\n                ...(durationSeconds !== undefined ? { durationSeconds } : {}),\n                raw: { tag, value, earlyDetection: true },\n              } as Scte35Marker;\n\n              if (this.debug) {\n                console.log(\"[StormcloudVideoPlayer] EARLY SCTE-35 DETECTION: Ad break marker found in fragment\", i, \"- starting pre-fetch (NOT playing yet)\");\n              }\n\n              this.callbacks.onScte35Cue(marker, {\n                ...this.cueManager.createScte35CueContext(\"manifest\", \"early\", frag),\n              });\n              return;\n            }\n          }\n        }\n      }\n    });\n\n    this.hls.on(Hls.Events.FRAG_BUFFERED, async (_evt, _data: any) => {\n      if (this.hasInitialBufferCompleted) {\n        return;\n      }\n\n      this.bufferedSegmentsCount++;\n      const minSegments = this.config.minSegmentsBeforePlay ?? 2;\n\n      if (this.debug) {\n        console.log(\n          `[StormcloudVideoPlayer] Buffered segment ${this.bufferedSegmentsCount}/${minSegments}`\n        );\n      }\n\n      if (this.bufferedSegmentsCount >= minSegments) {\n        this.hasInitialBufferCompleted = true;\n\n        if (this.shouldAutoplayAfterBuffering) {\n          if (this.debug) {\n            console.log(\n              `[StormcloudVideoPlayer] Initial buffer complete (${this.bufferedSegmentsCount} segments). Starting playback.`\n            );\n          }\n          await this.video.play()?.catch((err) => {\n            if (this.debug) {\n              console.warn(\"[StormcloudVideoPlayer] Autoplay failed:\", err);\n            }\n          });\n        }\n      }\n    });\n\n    this.hls.on(Hls.Events.FRAG_PARSING_METADATA, (_evt, data: any) => {\n      const id3Tags: Id3TagInfo[] = (data?.samples || []).map((s: any) => ({\n        key: \"ID3\",\n        value: s?.data,\n        ptsSeconds: s?.pts,\n      }));\n      id3Tags.forEach((tag) => this.onId3Tag(tag));\n    });\n\n    this.hls.on(Hls.Events.FRAG_LOADED, (_evt, data: any) => {\n      this.processFragmentScte35Payload(\n        data?.payload,\n        typeof data?.frag?.sn === \"number\" ? data.frag.sn : undefined,\n        getFragmentStartSeconds(data?.frag)\n      );\n    });\n\n    this.hls.on(Hls.Events.FRAG_DECRYPTED, (_evt, data: any) => {\n      this.processFragmentScte35Payload(\n        data?.payload,\n        typeof data?.frag?.sn === \"number\" ? data.frag.sn : undefined,\n        getFragmentStartSeconds(data?.frag)\n      );\n    });\n\n    this.hls.on(Hls.Events.FRAG_CHANGED, (_evt, data: any) => {\n      const frag = data?.frag;\n      const tagList: any[] | undefined = frag?.tagList;\n      if (!Array.isArray(tagList)) {\n        this.callbacks.activatePendingCuesForFragment(frag);\n        return;\n      }\n\n      for (const entry of tagList) {\n        let tag = \"\";\n        let value = \"\";\n        if (Array.isArray(entry)) {\n          tag = String(entry[0] ?? \"\");\n          value = String(entry[1] ?? \"\");\n        } else if (typeof entry === \"string\") {\n          const idx = entry.indexOf(\":\");\n          if (idx >= 0) {\n            tag = entry.substring(0, idx);\n            value = entry.substring(idx + 1);\n          } else {\n            tag = entry;\n            value = \"\";\n          }\n        }\n\n        if (!tag) continue;\n        if (tag.includes(\"EXT-X-CUE-OUT-CONT\")) {\n          const prog = parseCueOutCont(value);\n          const marker: Scte35Marker = {\n            type: \"progress\",\n            ...(prog?.duration !== undefined\n              ? { durationSeconds: prog.duration }\n              : {}),\n            ...(prog?.elapsed !== undefined\n              ? { ptsSeconds: prog.elapsed }\n              : {}),\n            raw: { tag, value },\n          } as Scte35Marker;\n          this.callbacks.onScte35Cue(marker, {\n            ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag),\n          });\n        } else if (tag.includes(\"EXT-X-CUE-OUT\")) {\n          const durationSeconds = parseCueOutDuration(value);\n          const marker: Scte35Marker = {\n            type: \"start\",\n            ...(durationSeconds !== undefined ? { durationSeconds } : {}),\n            raw: { tag, value },\n          } as Scte35Marker;\n          this.callbacks.onScte35Cue(marker, {\n            ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag),\n          });\n        } else if (tag.includes(\"EXT-X-CUE-IN\")) {\n          this.callbacks.onScte35Cue(\n            { type: \"end\", raw: { tag, value } },\n            {\n              ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag),\n            }\n          );\n        } else if (tag.includes(\"EXT-X-DATERANGE\")) {\n          const attrs = parseAttributeList(value);\n          const hasScteOut =\n            \"SCTE35-OUT\" in attrs || attrs[\"SCTE35-OUT\"] !== undefined;\n          const hasScteIn =\n            \"SCTE35-IN\" in attrs || attrs[\"SCTE35-IN\"] !== undefined;\n          const klass = String(attrs[\"CLASS\"] ?? \"\");\n          const duration = toNumber(attrs[\"DURATION\"]);\n\n          if (hasScteOut || /com\\.apple\\.hls\\.cue/i.test(klass)) {\n            const marker: Scte35Marker = {\n              type: \"start\",\n              ...(duration !== undefined ? { durationSeconds: duration } : {}),\n              raw: { tag, value, attrs },\n            } as Scte35Marker;\n            this.callbacks.onScte35Cue(marker, {\n              ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag),\n            });\n          }\n          if (hasScteIn) {\n            this.callbacks.onScte35Cue(\n              { type: \"end\", raw: { tag, value, attrs } },\n              {\n                ...this.cueManager.createScte35CueContext(\"manifest\", \"playback\", frag),\n              }\n            );\n          }\n        }\n      }\n      this.callbacks.activatePendingCuesForFragment(frag);\n    });\n\n    this.hls.on(Hls.Events.ERROR, (_evt, data) => {\n      if (data?.fatal) {\n        switch (data.type) {\n          case Hls.ErrorTypes.NETWORK_ERROR:\n            this.hls?.startLoad();\n            break;\n          case Hls.ErrorTypes.MEDIA_ERROR:\n            this.hls?.recoverMediaError();\n            break;\n          default:\n            this.callbacks.onFatalDestroy();\n            break;\n        }\n      }\n    });\n\n    this.hls.attachMedia(this.video);\n  }\n\n  private onId3Tag(tag: Id3TagInfo): void {\n    if (typeof tag.ptsSeconds === \"number\") {\n      this.timing.updatePtsDrift(tag.ptsSeconds);\n    }\n    const marker = parseScte35FromId3(tag);\n    if (marker) {\n      this.callbacks.onScte35Cue(marker, {\n        source: \"id3\",\n        readiness: \"playback\",\n      });\n    }\n  }\n\n  private processFragmentScte35Payload(\n    payloadData: unknown,\n    fragmentSn?: number,\n    fragmentStartSeconds?: number\n  ): void {\n    const payload = normalizeFragmentPayload(payloadData);\n    if (!payload) {\n      return;\n    }\n\n    const markers = parseScte35FromTsPackets(\n      payload,\n      this.cueManager.tsScte35Pids,\n      this.cueManager.pmtPids,\n      this.cueManager.processedTsScte35Sections\n    );\n    markers.forEach((marker) => {\n      const context: Scte35CueContext = {\n        source: \"ts\",\n        readiness: \"early\",\n      };\n      if (fragmentSn !== undefined) {\n        context.fragmentSn = fragmentSn;\n      }\n      if (fragmentStartSeconds !== undefined) {\n        context.fragmentStartSeconds = fragmentStartSeconds;\n      }\n      this.callbacks.onScte35Cue(marker, context);\n    });\n  }\n\n  getLiveSyncPosition(): number | undefined {\n    const pos = this.hls?.liveSyncPosition;\n    return typeof pos === \"number\" && Number.isFinite(pos) ? pos : undefined;\n  }\n\n  restartLoadAt(position: number): void {\n    if (!this.hls) {\n      return;\n    }\n    try {\n      this.hls.stopLoad();\n      this.hls.startLoad(position);\n    } catch (error) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to restart HLS load at live edge:\", error);\n      }\n    }\n  }\n\n  recoverMediaError(): void {\n    if (!this.hls) {\n      return;\n    }\n    try {\n      this.hls.recoverMediaError();\n    } catch (error) {\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] recoverMediaError() failed:\", error);\n      }\n    }\n  }\n\n  reloadLiveStream(): void {\n    const hls = this.hls;\n    if (!hls) {\n      return;\n    }\n    if (this.debug) {\n      console.log(\"[StormcloudVideoPlayer] Hard-reloading live stream (detach → reset video → re-attach)\");\n    }\n    try {\n      this.reloadingLiveStream = true;\n      hls.stopLoad();\n      hls.detachMedia();\n      try {\n        this.video.removeAttribute(\"src\");\n        this.video.load();\n      } catch (error) {\n        console.warn(\"[StormcloudVideoPlayer] video.load() threw after src removal:\", error);\n      }\n      hls.attachMedia(this.video);\n    } catch (error) {\n      this.reloadingLiveStream = false;\n      if (this.debug) {\n        console.warn(\"[StormcloudVideoPlayer] Failed to hard-reload live stream:\", error);\n      }\n    }\n  }\n\n  destroy(): void {\n    this.hls?.destroy();\n    this.hls = undefined;\n  }\n}\n","import type { AdController } from \"../types\";\n\nexport function getAdAudioVolume(adPlayer: AdController): number {\n  return adPlayer.getOriginalMutedState() ? 0 : adPlayer.getOriginalVolume();\n}\n\nexport function toggleMute(\n  video: HTMLVideoElement,\n  adPlayer: AdController,\n  debug: boolean\n): void {\n  if (adPlayer.isAdPlaying()) {\n    const newMutedState = !adPlayer.getOriginalMutedState();\n    const restoreVolume = adPlayer.getOriginalVolume() || 1;\n\n    adPlayer.updateOriginalMutedState(newMutedState, video.volume);\n    adPlayer.setAdVolume(newMutedState ? 0 : restoreVolume);\n\n    if (debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] Mute toggle during ad - immediately applied:\",\n        newMutedState\n      );\n    }\n  } else {\n    video.muted = !video.muted;\n    adPlayer.updateOriginalMutedState(video.muted, video.volume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] Muted:\", video.muted);\n    }\n  }\n}\n\nexport function toggleFullscreen(\n  video: HTMLVideoElement,\n  debug: boolean\n): Promise<void> {\n  return new Promise((resolve, reject) => {\n    if (!document.fullscreenElement) {\n      const container = video.parentElement;\n      if (!container) {\n        reject(new Error(\"No parent container found for fullscreen\"));\n        return;\n      }\n      container\n        .requestFullscreen()\n        .then(() => {\n          if (debug) {\n            console.log(\"[StormcloudVideoPlayer] Entered fullscreen\");\n          }\n          resolve();\n        })\n        .catch((err) => {\n          if (debug) {\n            console.error(\"[StormcloudVideoPlayer] Fullscreen error:\", err);\n          }\n          reject(err);\n        });\n    } else {\n      document\n        .exitFullscreen()\n        .then(() => {\n          if (debug) {\n            console.log(\"[StormcloudVideoPlayer] Exited fullscreen\");\n          }\n          resolve();\n        })\n        .catch((err) => {\n          if (debug) {\n            console.error(\n              \"[StormcloudVideoPlayer] Exit fullscreen error:\",\n              err\n            );\n          }\n          reject(err);\n        });\n    }\n  });\n}\n\nexport function isMuted(\n  video: HTMLVideoElement,\n  adPlayer: AdController\n): boolean {\n  if (adPlayer.isAdPlaying()) {\n    return adPlayer.getOriginalMutedState();\n  }\n  return video.muted;\n}\n\nexport function setMuted(\n  video: HTMLVideoElement,\n  adPlayer: AdController,\n  muted: boolean,\n  debug: boolean\n): void {\n  const adPlaying = adPlayer.isAdPlaying();\n\n  if (adPlaying && muted === video.muted) {\n    if (debug) {\n      console.log(\n        \"[StormcloudVideoPlayer] setMuted reflective update during ad ignored\",\n        { muted }\n      );\n    }\n    return;\n  }\n\n  video.muted = muted;\n\n  if (adPlaying) {\n    adPlayer.updateOriginalMutedState(muted, video.volume);\n    adPlayer.setAdVolume(muted ? 0 : 1);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setMuted applied during ad\", {\n        muted,\n      });\n    }\n    return;\n  }\n\n  adPlayer.updateOriginalMutedState(muted, video.volume);\n  if (debug) {\n    console.log(\"[StormcloudVideoPlayer] setMuted called:\", muted);\n  }\n}\n\nexport function setVolume(\n  video: HTMLVideoElement,\n  adPlayer: AdController,\n  volume: number,\n  debug: boolean\n): void {\n  const clampedVolume = Math.max(0, Math.min(1, volume));\n  const adPlaying = adPlayer.isAdPlaying();\n\n  if (adPlaying) {\n    adPlayer.setAdVolume(clampedVolume);\n    adPlayer.updateOriginalMutedState(clampedVolume === 0, clampedVolume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setVolume applied during ad\", {\n        volume: clampedVolume,\n      });\n    }\n  } else {\n    video.volume = clampedVolume;\n    video.muted = clampedVolume === 0;\n    adPlayer.updateOriginalMutedState(clampedVolume === 0, clampedVolume);\n    if (debug) {\n      console.log(\"[StormcloudVideoPlayer] setVolume called:\", clampedVolume);\n    }\n  }\n}\n\nexport function getVolume(\n  video: HTMLVideoElement,\n  adPlayer: AdController\n): number {\n  const adPlaying = adPlayer.isAdPlaying();\n  if (adPlaying) {\n    return adPlayer.getAdVolume();\n  }\n  return video.volume;\n}\n\nexport function isFullscreen(): boolean {\n  return !!document.fullscreenElement;\n}\n\nexport function resizePlayer(\n  video: HTMLVideoElement,\n  adPlayer: AdController,\n  debug: boolean\n): void {\n  if (debug) {\n    console.log(\"[StormcloudVideoPlayer] Resizing player\");\n  }\n\n  if (adPlayer && adPlayer.isAdPlaying()) {\n    const width = video.clientWidth || 640;\n    const height = video.clientHeight || 480;\n\n    if (debug) {\n      console.log(\n        `[StormcloudVideoPlayer] Resizing ads manager to ${width}x${height}`\n      );\n    }\n\n    adPlayer.resize(width, height);\n  }\n}\n"]}