@@ -3,7 +3,7 @@ import type { WrappedFunction } from '../types-hoist';
33
44import { htmlTreeAsString } from './browser' ;
55import { DEBUG_BUILD } from './debug-build' ;
6- import { isElement , isError , isEvent , isInstanceOf , isPlainObject , isPrimitive } from './is' ;
6+ import { isElement , isError , isEvent , isInstanceOf , isPrimitive } from './is' ;
77import { logger } from './logger' ;
88import { truncate } from './string' ;
99
@@ -222,58 +222,55 @@ export function dropUndefinedKeys<T>(inputValue: T): T {
222222}
223223
224224function _dropUndefinedKeys < T > ( inputValue : T , memoizationMap : Map < unknown , unknown > ) : T {
225- if ( isPojo ( inputValue ) ) {
226- // If this node has already been visited due to a circular reference, return the object it was mapped to in the new object
227- const memoVal = memoizationMap . get ( inputValue ) ;
228- if ( memoVal !== undefined ) {
229- return memoVal as T ;
230- }
231-
232- const returnValue : { [ key : string ] : unknown } = { } ;
233- // Store the mapping of this value in case we visit it again, in case of circular data
234- memoizationMap . set ( inputValue , returnValue ) ;
235-
236- for ( const key of Object . getOwnPropertyNames ( inputValue ) ) {
237- if ( typeof inputValue [ key ] !== 'undefined' ) {
238- returnValue [ key ] = _dropUndefinedKeys ( inputValue [ key ] , memoizationMap ) ;
239- }
240- }
225+ // Early return for primitive values
226+ if ( inputValue === null || typeof inputValue !== 'object' ) {
227+ return inputValue ;
228+ }
241229
242- return returnValue as T ;
230+ // Check memo map first for all object types
231+ const memoVal = memoizationMap . get ( inputValue ) ;
232+ if ( memoVal !== undefined ) {
233+ return memoVal as T ;
243234 }
244235
236+ // handle arrays
245237 if ( Array . isArray ( inputValue ) ) {
246- // If this node has already been visited due to a circular reference, return the array it was mapped to in the new object
247- const memoVal = memoizationMap . get ( inputValue ) ;
248- if ( memoVal !== undefined ) {
249- return memoVal as T ;
250- }
251-
252238 const returnValue : unknown [ ] = [ ] ;
253- // Store the mapping of this value in case we visit it again, in case of circular data
239+ // Store mapping to handle circular references
254240 memoizationMap . set ( inputValue , returnValue ) ;
255241
256- inputValue . forEach ( ( item : unknown ) => {
257- returnValue . push ( _dropUndefinedKeys ( item , memoizationMap ) ) ;
242+ inputValue . forEach ( value => {
243+ returnValue . push ( _dropUndefinedKeys ( value , memoizationMap ) ) ;
258244 } ) ;
259245
260246 return returnValue as unknown as T ;
261247 }
262248
249+ if ( isPojo ( inputValue ) ) {
250+ const returnValue : { [ key : string ] : unknown } = { } ;
251+ // Store mapping to handle circular references
252+ memoizationMap . set ( inputValue , returnValue ) ;
253+
254+ const keys = Object . keys ( inputValue ) ;
255+
256+ keys . forEach ( key => {
257+ const val = inputValue [ key ] ;
258+ if ( val !== undefined ) {
259+ returnValue [ key ] = _dropUndefinedKeys ( val , memoizationMap ) ;
260+ }
261+ } ) ;
262+
263+ return returnValue as T ;
264+ }
265+
266+ // For other object types, return as is
263267 return inputValue ;
264268}
265269
266270function isPojo ( input : unknown ) : input is Record < string , unknown > {
267- if ( ! isPlainObject ( input ) ) {
268- return false ;
269- }
270-
271- try {
272- const name = ( Object . getPrototypeOf ( input ) as { constructor : { name : string } } ) . constructor . name ;
273- return ! name || name === 'Object' ;
274- } catch {
275- return true ;
276- }
271+ // Plain objects have Object as constructor or no constructor
272+ const constructor = ( input as object ) . constructor ;
273+ return constructor === Object || constructor === undefined ;
277274}
278275
279276/**
0 commit comments