UNPKG

@faberto/core-web

Version:

Nimiq's Rust-to-WASM web client

72 lines (64 loc) 2.79 kB
/** * @typedef {import("./bundler/index").PlainClientConfiguration} PlainClientConfiguration * @typedef {import("./bundler/index").Client} Client */ /** * @param {() => Worker} workerFactory * @param {*} Comlink * @returns {{create(config: PlainClientConfiguration): Promise<Client>}} */ export function clientFactory(workerFactory, Comlink) { // Expose Client "class" with one static `create` method return { /** * * @param {PlainClientConfiguration} config * @returns {Promise<Client>} */ async create(config) { const worker = workerFactory(); // Wait for worker script to load await new Promise((resolve) => { const readyListener = (event) => { worker.removeEventListener('message', readyListener); if (event.data === 'NIMIQ_ONLOAD') resolve(); }; worker.addEventListener('message', readyListener); }); // Wrap the worker with Comlink, to transparently proxy any method calls on the client // instance to the worker. // ATTENTION: The receiver in the worker is only available after the initialization // below completes. const client = Comlink.wrap(worker); // Send offline/online/visible events from the main thread, as Chromium-based browsers // do not support these events in web workers: // https://bugs.chromium.org/p/chromium/issues/detail?id=114475 window.addEventListener('offline', () => worker.postMessage('offline')); window.addEventListener('online', () => worker.postMessage('online')); document.addEventListener('visibilitychange', () => { if (document.visibilityState === "visible") { worker.postMessage('visible'); } }); // Create the client with the config in the worker console.log('Sending NIMIQ_INIT message to worker'); worker.postMessage({ type: 'NIMIQ_INIT', config, }); await new Promise((resolve, reject) => { worker.addEventListener('message', (event) => { if (!('ok' in event.data)) return; if (event.data.ok === true) resolve(); if (event.data.ok === false) { const error = new Error(event.data.error); error.stack = event.data.stack; reject(error); } }); }); console.log('Have worker client'); return client; }, }; };