'use strict' ; import H from '../Core/Globals.js' ; const win = H . win ; const delay = setTimeout ; /**
 * Simplified wrapper for Promise-support in outdated browsers.
 */ class DataPromise < T > implements Promise < T > { public static onlyPolyfill = false ; private static isPromiseLike < T > ( promise ) { return ( typeof promise === 'object' && promise !== null && typeof ( promise as PromiseLike < T > ) . then === 'function' ) ; } public static reject < T = never > ( reason ) { if ( win . Promise && ! DataPromise . onlyPolyfill ) { return win . Promise . reject ( reason ) ; } return new DataPromise < T > ( ( resolve , reject ) : void => reject ( reason ) ) ; } public static resolve < T > ( value ) ; public static resolve < T > ( ) ; public static resolve < T > ( value ? ) { if ( win . Promise && ! DataPromise . onlyPolyfill ) { return win . Promise . resolve ( value ) ; } if ( DataPromise . isPromiseLike ( value ) ) { return new DataPromise ( ( resolve , reject ) : void => { value . then ( resolve , reject ) ; } ) ; } return new DataPromise ( ( resolve ) : void => resolve ( value ) ) ; } public constructor ( executor ) { if ( win . Promise && ! DataPromise . onlyPolyfill ) { return new win . Promise ( executor ) ; } const promise = this ; delay ( ( ) : void => { try { executor ( ( value ? ) : void => promise . resolved ( value ) , ( reason ? ) : void => promise . rejected ( reason ) ) ; } catch ( e ) { promise . rejected ( e ) ; } } , 0 ) ; } private readonly jobs : Array < DataPromise . Job < T > > = [ ] ; private reason : unknown ; private state = DataPromise . State . Pending ; private value : T = void 0 as unknown as T ; public 'catch' < TResult = never > ( onrejected ? ) { return this . then ( null , onrejected ) ; } private rejected ( reason ? ) { const promise = this ; if ( promise . state === DataPromise . State . Pending ) { promise . state = DataPromise . State . Rejected ; promise . reason = reason ; delay ( ( ) : void => promise . work ( ) , 0 ) ; } } private resolved ( value ? ) { const promise = this ; if ( promise . state === DataPromise . State . Pending ) { if ( DataPromise . isPromiseLike ( value ) ) { value . then ( ( value ) : void => promise . resolved ( value ) , ( reason ) : void => promise . rejected ( reason ) ) ; } else { promise . state = DataPromise . State . Fulfilled ; promise . value = value as T ; delay ( ( ) : void => promise . work ( ) , 0 ) ; } } } public then < TResult1 = T , TResult2 = never > ( onfulfilled ? , onrejected ? ) { const promise = this , newPromise = new DataPromise < ( TResult1 | TResult2 ) > ( ( ) : void => void 0 ) , rejecter = ( reason ) : void => { if ( onrejected ) { try { const result = onrejected ( reason ) ; if ( result instanceof DataPromise ) { result . then ( ( value ? ) : void => newPromise . resolved ( value ) , ( reason ? ) : void => newPromise . rejected ( reason ) ) ; } else { newPromise . resolved ( result ) ; } return ; } catch ( e ) { reason = e ; } } if ( newPromise . jobs . length ) { newPromise . rejected ( reason ) ; } else if ( reason ) { throw reason ; } else { throw new Error ( 'Unhandled exception' ) ; } } , resolver = ( value ) : void => { if ( onfulfilled ) { try { const result = onfulfilled ( value ) ; if ( result instanceof DataPromise ) { result . then ( ( value ? ) : void => newPromise . resolved ( value ) , ( reason ? ) : void => newPromise . rejected ( reason ) ) ; } else { newPromise . resolved ( result ) ; } } catch ( e ) { rejecter ( e ) ; } } else { newPromise . resolved ( value as unknown as TResult1 ) ; } } ; switch ( promise . state ) { case DataPromise . State . Fulfilled : resolver ( promise . value ) ; break ; case DataPromise . State . Rejected : rejecter ( promise . reason ) ; break ; default : promise . jobs . push ( { resolve : resolver , reject : rejecter } ) ; break ; } return newPromise ; } private work ( ) { const promise = this , jobs = promise . jobs ; let job , rejectHandled ; while ( ( job = jobs . shift ( ) ) ) { try { if ( promise . state === DataPromise . State . Fulfilled ) { job . resolve ( promise . value ) ; } else if ( job . reject ) { rejectHandled = true ; job . reject ( promise . reason ) ; } } catch ( e ) { rejectHandled = false ; promise . reason = e ; promise . state = DataPromise . State . Rejected ; } } if ( rejectHandled === false ) { if ( promise . reason ) { throw promise . reason ; } else { throw new Error ( 'Unhandled rejection' ) ; } } } } interface DataPromise < T > extends Promise < T > { } namespace DataPromise { export interface Job < T > { resolve : ( value : T ) => void ; reject : ( reason : unknown ) => void ; } export enum State { Fulfilled = 2 , Pending = 0 , Rejected = 1 } } export default DataPromise ;