import { isNumber , isString } from '@utils' ; import { MsgFromWorker , MsgToWorker , WorkerMsgHandler } from '../../../declarations' ; export const initWebWorkerThread = ( msgHandler ) => { let isQueued = false ; const tick = Promise . resolve ( ) ; const msgsFromWorkerQueue = [ ] ; const drainMsgQueueFromWorkerToMain = ( ) => { isQueued = false ; ( self as any ) . postMessage ( msgsFromWorkerQueue ) ; msgsFromWorkerQueue . length = 0 ; } ; const queueMsgFromWorkerToMain = ( msgFromWorkerToMain ) => { msgsFromWorkerQueue . push ( msgFromWorkerToMain ) ; if ( ! isQueued ) { isQueued = true ; tick . then ( drainMsgQueueFromWorkerToMain ) ; } } ; const error = ( stencilMsgId , err ) => { const errMsgFromWorkerToMain = { stencilId : stencilMsgId , stencilRtnValue : null , stencilRtnError : 'Error' , } ; if ( isString ( err ) ) { errMsgFromWorkerToMain . stencilRtnError += ': ' + err ; } else if ( err ) { if ( err . stack ) { errMsgFromWorkerToMain . stencilRtnError += ': ' + err . stack ; } else if ( err . message ) { errMsgFromWorkerToMain . stencilRtnError += ': ' + err . message ; } } queueMsgFromWorkerToMain ( errMsgFromWorkerToMain ) ; } ; const receiveMsgFromMainToWorker = async ( msgToWorker ) => { if ( msgToWorker && isNumber ( msgToWorker . stencilId ) ) { try { const msgFromWorkerToMain = { stencilId : msgToWorker . stencilId , stencilRtnValue : await msgHandler ( msgToWorker ) , stencilRtnError : null , } ; queueMsgFromWorkerToMain ( msgFromWorkerToMain ) ; } catch ( e ) { error ( msgToWorker . stencilId , e ) ; } } } ; self . onmessage = ( ev ) => { const msgsFromMainToWorker = ev . data ; if ( Array . isArray ( msgsFromMainToWorker ) ) { for ( const msgFromMainToWorker of msgsFromMainToWorker ) { receiveMsgFromMainToWorker ( msgFromMainToWorker ) ; } } } ; self . onerror = ( e ) => { error ( - 1 , e ) ; } ; } ;