UNPKG

@wordpress/data

Version:
60 lines (54 loc) 1.63 kB
/** * External dependencies */ import type { AnyAction, Reducer } from 'redux'; /** * Higher-order reducer creator which creates a combined reducer object, keyed * by a property on the action object. * * @param actionProperty Action property by which to key object. * @return Higher-order reducer. */ export const onSubKey = < TState extends unknown, TAction extends AnyAction >( actionProperty: string ) => ( reducer: Reducer< TState, TAction > ): Reducer< Record< string, TState >, TAction > => ( state: Record< string, TState > = {}, action ) => { // Retrieve subkey from action. Do not track if undefined; useful for cases // where reducer is scoped by action shape. const key = action[ actionProperty ]; if ( key === undefined ) { return state; } // Avoid updating state if unchanged. Note that this also accounts for a // reducer which returns undefined on a key which is not yet tracked. const nextKeyState = reducer( state[ key ], action ); if ( nextKeyState === state[ key ] ) { return state; } return { ...state, [ key ]: nextKeyState, }; }; /** * Normalize selector argument array by defaulting `undefined` value to an empty array * and removing trailing `undefined` values. * * @param args Selector argument array * @return Normalized state key array */ export function selectorArgsToStateKey( args: unknown[] | null | undefined ) { if ( args === undefined || args === null ) { return []; } const len = args.length; let idx = len; while ( idx > 0 && args[ idx - 1 ] === undefined ) { idx--; } return idx === len ? args : args.slice( 0, idx ); }