UNPKG

poll-until-promise

Version:

Try repeatedly for a promise to be resolved

160 lines (126 loc) 3.89 kB
[![NPM Version][npm-image]][npm-url] ![Build](https://github.com/AlonMiz/poll-until-promise/actions/workflows/nodejs.yml/badge.svg) # Poll Until Promise Wait until the executed promise resolved to a true value, Execute it every x milliseconds and stop after y milliseconds. ## Install `npm install poll-until-promise` ## Usage ### Fetching data ```js const { waitFor } = require('poll-until-promise'); waitFor(() => fetch('/get-data'), { interval: 100 }) // Tries every 100ms (from the last failure) .then(value => console.log('Yey', value)) .catch(err => console.error(err)); ``` ### Using async ```js import { waitFor, AbortError } from 'poll-until-promise'; async function waitForDomElement(cssSelector = 'div') { try { const element = await waitFor(() => { const element = window.document.querySelector(cssSelector); if (!element) throw new Error(`failed to find element: ${cssSelector}`); return element; }, { timeout: 60_000 }); return element; } catch (e) { console.error('faled to find dom element:', e); throw e; } } async function retryFetch(path = '/get-data') { try { const data = await waitFor(async () => { const res = await fetch(path); // Stop immediately if the resource doesn't exist if (res.status === 404) { throw new AbortError(res.statusText); } return res.json(); }, { timeout: 60_000, interval: 1000 }); } catch (e) { console.error('faled to fetch:', e); throw e; } } ``` ### Waiting for something to be successful ```js const { waitFor } = require('poll-until-promise'); waitFor(() => { if (Math.random() >= 0.5) { throw new Error('try again'); } else { console.log('all good') } }) .then(() => console.log('Yey')) .catch(err => console.error(err)); ``` ### Using the class ```js const { PollUntil } = require('poll-until-promise'); const later = Date.now() + 1000; // 1 seconds into the future let pollUntilPromise = new PollUntil(); pollUntilPromise .stopAfter(2 * 1000) // Stop trying after 2 seconds .tryEvery(100) // Tries every 100ms (from the last failure) .execute(() => { return new Promise((resolve, reject) => { if (+Date.now() >= later) { return resolve(true); // Some truthy value } reject(false); }) }) .then(value => console.log('Yey', value)) .catch(err => console.error(err)); ``` ## Options ```js const options = { interval: 100, backoffFactor: 1, // Exponential interval increase. Defaults to 1, which means no backoff backoffMaxInterval: 250, // Sets a maximum interval when using backoff. Defaults to the timeout value timeout: 1000, stopOnFailure: false, // Ignores promise rejections verbose: false, message: 'Waiting for time to pass :)', // custom message to display on failure maxAttempts: 5, // maximum attempts to make (default: no limit). Will still fail to wait if reaching timeout before attempts exhausted }; let pollUntilPromise = new PollUntil(options); ``` ## Methods * isResolved ```js pollUntilPromise.isResolved() ``` * isWaiting ```js pollUntilPromise.isWaiting() ``` * getPromise ```js pollUntilPromise.getPromise().then(() => console.log('OMG')) ``` ## Static Function ```js const PollUntil = require('poll-until-promise'); const later = Date.now() + 1000; // 1 seconds into the future let pollUntilPromise = new PollUntil(); pollUntilPromise .stopAfter(2 * 1000) .tryEvery(100) .execute(() => { if (+Date.now() >= later) { return true; } return false; }) .then((value) => console.log('Yey', value)) .catch((err) => console.error(err)); ``` [npm-url]: https://npmjs.org/package/poll-until-promise [npm-image]: https://img.shields.io/npm/v/poll-until-promise.svg