/** * WordPress dependencies */ import apiFetch from '@safe-wordpress/api-fetch'; import { dispatch, select } from '@safe-wordpress/data'; import { addQueryArgs } from '@safe-wordpress/url'; /** * External dependencies */ import { logError } from '@nelio-content/utils'; import type { Author, AuthorId } from '@nelio-content/types'; /** * Internal dependencies */ import { store as NC_DATA } from '../../../store'; export async function loadAuthors( authorIds: ReadonlyArray< AuthorId > ): Promise< void > { const ids = unique( authorIds ).filter( ( authorId ) => ! select( NC_DATA ).hasAuthor( authorId ) ); ids.forEach( ( id ) => pendingAuthorIds.add( id ) ); if ( ! pendingAuthorIds.size ) { return; } pendingAuthorRequest = pendingAuthorRequest ?? flushPendingAuthorIds(); await pendingAuthorRequest; } async function flushPendingAuthorIds(): Promise< void > { try { await waitForBatchWindow(); while ( pendingAuthorIds.size ) { const ids = Array.from( pendingAuthorIds ).filter( ( authorId ) => ! select( NC_DATA ).hasAuthor( authorId ) ); pendingAuthorIds.clear(); if ( ! ids.length ) { continue; } const authors = await apiFetch< ReadonlyArray< Author > >( { path: addQueryArgs( '/nelio-content/v1/author/batch', { ids: ids.join( ',' ), } ), } ); await dispatch( NC_DATA ).receiveAuthors( authors ); } } catch ( e ) { logError( e ); } finally { pendingAuthorRequest = undefined; } } const unique = < T >( values: ReadonlyArray< T > ): ReadonlyArray< T > => Array.from( new Set( values ) ); const waitForBatchWindow = () => new Promise< void >( ( resolve ) => setTimeout( resolve, 50 ) ); const pendingAuthorIds = new Set< AuthorId >(); let pendingAuthorRequest: Promise< void > | undefined;