@atlaskit/editor-common
Version:
A package that contains common classes and components for editor and renderer
61 lines (56 loc) • 2.25 kB
JavaScript
import { getOnlyFulfilled, waitForAllPromises, waitForFirstFulfilledPromise } from './promise-helpers';
const flatten = arr => [].concat(...arr);
/**
* Allow to run methods from the given provider interface across all providers seamlessly.
* Handles promise racing and discards rejected promises safely.
*/
export default (providers => {
if (providers.length === 0) {
throw new Error('At least one provider must be provided');
}
const getFulfilledProviders = async () => {
const results = await waitForAllPromises(providers.map(result => Promise.resolve(result)));
// Filter out null/undefined providers to prevent errors when calling methods on them
return getOnlyFulfilled(results).filter(provider => provider != null);
};
const runInAllProviders = async mapFunction => {
return (await getFulfilledProviders()).map(provider => mapFunction(provider));
};
// Ignored via go/ees005
// eslint-disable-next-line @typescript-eslint/no-explicit-any
const createCallback = (methodName, args) => provider => {
const method = provider[methodName];
if (typeof method === 'function') {
return method.apply(provider, args);
}
throw new Error(`"${String(methodName)}" isn't a function of the provider`);
};
/**
* Run a method from the provider which expects to return a single item
* @param methodName
* @param args
*/
// Ignored via go/ees005
// eslint-disable-next-line @typescript-eslint/no-explicit-any
const invokeSingle = async (methodName, args) => {
const callback = createCallback(methodName, args);
return waitForFirstFulfilledPromise(await runInAllProviders(callback));
};
/**
* Run a method in the provider which expectes to return a list of items
* @param methodName
* @param args
*/
// Ignored via go/ees005
// eslint-disable-next-line @typescript-eslint/no-explicit-any
const invokeList = async (methodName, args) => {
const callback = createCallback(methodName, args);
const results = await waitForAllPromises(await runInAllProviders(callback));
const fulfilledResults = getOnlyFulfilled(results);
return flatten(fulfilledResults).filter(result => result);
};
return {
invokeSingle,
invokeList
};
});