@rudderstack/analytics-js 3.11.6 → 3.11.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -273,6 +273,10 @@ const isFunction=value=>typeof value==='function'&&Boolean(value.constructor&&va
273
273
  * @param value input value
274
274
  * @returns boolean
275
275
  */const isNullOrUndefined=value=>isNull(value)||isUndefined(value);/**
276
+ * Checks if the input is a BigInt
277
+ * @param value input value
278
+ * @returns True if the input is a BigInt
279
+ */const isBigInt=value=>typeof value==='bigint';/**
276
280
  * A function to check given value is defined
277
281
  * @param value input value
278
282
  * @returns boolean
@@ -290,6 +294,8 @@ const isFunction=value=>typeof value==='function'&&Boolean(value.constructor&&va
290
294
  * @returns true if the input is an instance of Error and false otherwise
291
295
  */const isTypeOfError=obj=>obj instanceof Error;
292
296
 
297
+ const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
298
+
293
299
  const getValueByPath=(obj,keyPath)=>{const pathParts=keyPath.split('.');return path(pathParts,obj);};const hasValueByPath=(obj,path)=>Boolean(getValueByPath(obj,path));const isObject=value=>typeof value==='object';/**
294
300
  * Checks if the input is an object literal or built-in object type and not null
295
301
  * @param value Input value
@@ -311,7 +317,28 @@ mergeDeepRight(mergedArray[index],value):value;});return mergedArray;};const mer
311
317
  * A utility to recursively remove undefined and null values from an object
312
318
  * @param obj input object
313
319
  * @returns a new object
314
- */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};
320
+ */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};const getReplacer=logger=>{const ancestors=[];// Array to track ancestor objects
321
+ // Using a regular function to use `this` for the parent context
322
+ return function replacer(key,value){if(isBigInt(value)){return '[BigInt]';// Replace BigInt values
323
+ }// `this` is the object that value is contained in, i.e., its direct parent.
324
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
325
+ // @ts-ignore-next-line
326
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();// Remove ancestors that are no longer part of the chain
327
+ }// Check for circular references (if the value is already in the ancestors)
328
+ if(ancestors.includes(value)){return '[Circular Reference]';}// Add current value to ancestors
329
+ ancestors.push(value);return value;};};const traverseWithThis=(obj,replacer)=>{// Create a new result object or array
330
+ const result=Array.isArray(obj)?[]:{};// Traverse object properties or array elements
331
+ // eslint-disable-next-line no-restricted-syntax
332
+ for(const key in obj){if(Object.hasOwnProperty.call(obj,key)){const value=obj[key];// Recursively apply the replacer and traversal
333
+ const sanitizedValue=replacer.call(obj,key,value);// If the value is an object or array, continue traversal
334
+ if(isObjectLiteralAndNotNull(sanitizedValue)||Array.isArray(sanitizedValue)){result[key]=traverseWithThis(sanitizedValue,replacer);}else {result[key]=sanitizedValue;}}}return result;};/**
335
+ * Recursively traverses an object similar to JSON.stringify,
336
+ * sanitizing BigInts and circular references
337
+ * @param value Input object
338
+ * @param logger Logger instance
339
+ * @returns Sanitized value
340
+ */const getSanitizedValue=(value,logger)=>{const replacer=getReplacer();// This is needed for registering the first ancestor
341
+ const newValue=replacer.call(value,'',value);if(isObjectLiteralAndNotNull(value)||Array.isArray(value)){return traverseWithThis(value,replacer);}return newValue;};
315
342
 
316
343
  const trim=value=>value.replace(/^\s+|\s+$/gm,'');const removeDoubleSpaces=value=>value.replace(/ {2,}/g,' ');const removeLeadingPeriod=value=>value.replace(/^\.+/,'');/**
317
344
  * A function to convert values to string
@@ -337,59 +364,37 @@ const trim=value=>value.replace(/^\s+|\s+$/gm,'');const removeDoubleSpaces=value
337
364
  * @returns decoded string
338
365
  */const fromBase64=value=>new TextDecoder().decode(base64ToBytes(value));
339
366
 
340
- const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
341
-
342
- const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
343
- // eslint-disable-next-line func-names
344
- return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
345
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
346
- // @ts-ignore-next-line
347
- while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
348
- * Utility method for JSON stringify object excluding null values & circular references
349
- *
350
- * @param {*} value input
351
- * @param {boolean} excludeNull if it should exclude nul or not
352
- * @param {function} logger optional logger methods for warning
353
- * @returns string
354
- */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};/**
355
- * Recursively traverses an object similar to JSON.stringify,
356
- * sanitizing BigInts and circular references
357
- * @param value Input object
358
- * @param logger Logger instance
359
- * @returns Sanitized value
360
- */const getSanitizedValue=(value,logger)=>value;
361
-
362
367
  // if yes make them null instead of omitting in overloaded cases
363
368
  /*
364
369
  * Normalise the overloaded arguments of the page call facade
365
- */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const sanitizedCategory=getSanitizedValue(category);const sanitizedName=getSanitizedValue(name);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={category:sanitizedCategory,name:sanitizedName,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}if(isFunction(sanitizedName)){payload.category=sanitizedCategory;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedName;}if(isFunction(sanitizedCategory)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedCategory;}if(isObjectLiteralAndNotNull(sanitizedCategory)){payload.name=undefined;payload.category=undefined;payload.properties=sanitizedCategory;if(!isFunction(sanitizedName)){payload.options=sanitizedName;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(sanitizedName)){payload.name=undefined;payload.properties=sanitizedName;if(!isFunction(sanitizedProperties)){payload.options=sanitizedProperties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
370
+ */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const payload={category:category,name:name,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.category=category;payload.name=name;payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.category=category;payload.name=name;payload.properties=undefined;payload.options=undefined;payload.callback=properties;}if(isFunction(name)){payload.category=category;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=name;}if(isFunction(category)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=category;}if(isObjectLiteralAndNotNull(category)){payload.name=undefined;payload.category=undefined;payload.properties=category;if(!isFunction(name)){payload.options=name;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(name)){payload.name=undefined;payload.properties=name;if(!isFunction(properties)){payload.options=properties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
366
371
  // use it as name and set category to undefined
367
- if(isString(sanitizedCategory)&&!isString(sanitizedName)){payload.category=undefined;payload.name=sanitizedCategory;}// Rest of the code is just to clean up undefined values
372
+ if(isString(category)&&!isString(name)){payload.category=undefined;payload.name=category;}// Rest of the code is just to clean up undefined values
368
373
  // and set some proper defaults
369
374
  // Also, to clone the incoming object type arguments
370
375
  if(!isDefined(payload.category)){payload.category=undefined;}if(!isDefined(payload.name)){payload.name=undefined;}payload.properties=payload.properties?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}const nameForProperties=isString(payload.name)?payload.name:payload.properties.name;const categoryForProperties=isString(payload.category)?payload.category:payload.properties.category;// add name and category to properties
371
376
  payload.properties=mergeDeepRight(isObjectLiteralAndNotNull(payload.properties)?payload.properties:{},{...(nameForProperties&&{name:nameForProperties}),...(categoryForProperties&&{category:categoryForProperties})});return payload;};/*
372
377
  * Normalise the overloaded arguments of the track call facade
373
- */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const sanitizedEvent=getSanitizedValue(event);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={name:sanitizedEvent,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}// Rest of the code is just to clean up undefined values
378
+ */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const payload={name:event,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.properties=undefined;payload.options=undefined;payload.callback=properties;}// Rest of the code is just to clean up undefined values
374
379
  // and set some proper defaults
375
380
  // Also, to clone the incoming object type arguments
376
381
  payload.properties=isDefinedAndNotNull(payload.properties)?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
377
382
  * Normalise the overloaded arguments of the identify call facade
378
- */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const sanitizedUserId=getSanitizedValue(userId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={userId:sanitizedUserId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.userId=sanitizedUserId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.userId=sanitizedUserId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedUserId)||isNull(sanitizedUserId)){// Explicitly set null to prevent resetting the existing value
383
+ */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const payload={userId:userId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.userId=userId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.userId=userId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(userId)||isNull(userId)){// Explicitly set null to prevent resetting the existing value
379
384
  // in the Analytics class
380
- payload.userId=null;payload.traits=sanitizedUserId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
385
+ payload.userId=null;payload.traits=userId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
381
386
  // and set some proper defaults
382
387
  // Also, to clone the incoming object type arguments
383
388
  payload.userId=tryStringify(payload.userId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
384
389
  * Normalise the overloaded arguments of the alias call facade
385
- */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const sanitizedTo=getSanitizedValue(to);const sanitizedFrom=getSanitizedValue(from);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={to:sanitizedTo,from:sanitizedFrom,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.to=sanitizedTo;payload.from=sanitizedFrom;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=undefined;payload.callback=sanitizedFrom;}else if(isObjectLiteralAndNotNull(sanitizedFrom)||isNull(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=sanitizedFrom;}// Rest of the code is just to clean up undefined values
390
+ */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const payload={to,from:from,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.to=to;payload.from=from;payload.options=undefined;payload.callback=options;}if(isFunction(from)){payload.to=to;payload.from=undefined;payload.options=undefined;payload.callback=from;}else if(isObjectLiteralAndNotNull(from)||isNull(from)){payload.to=to;payload.from=undefined;payload.options=from;}// Rest of the code is just to clean up undefined values
386
391
  // and set some proper defaults
387
392
  // Also, to clone the incoming object type arguments
388
393
  if(isDefined(payload.to)){payload.to=tryStringify(payload.to);}if(isDefined(payload.from)){payload.from=tryStringify(payload.from);}else {payload.from=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
389
394
  * Normalise the overloaded arguments of the group call facade
390
- */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const sanitizedGroupId=getSanitizedValue(groupId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={groupId:sanitizedGroupId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.groupId=sanitizedGroupId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.groupId=sanitizedGroupId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedGroupId)||isNull(sanitizedGroupId)){// Explicitly set null to prevent resetting the existing value
395
+ */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const payload={groupId:groupId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.groupId=groupId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.groupId=groupId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(groupId)||isNull(groupId)){// Explicitly set null to prevent resetting the existing value
391
396
  // in the Analytics class
392
- payload.groupId=null;payload.traits=sanitizedGroupId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
397
+ payload.groupId=null;payload.traits=groupId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
393
398
  // and set some proper defaults
394
399
  // Also, to clone the incoming object type arguments
395
400
  payload.groupId=tryStringify(payload.groupId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};
@@ -437,6 +442,20 @@ const getFormattedTimestamp=date=>date.toISOString();/**
437
442
  * @returns ISO formatted timestamp string
438
443
  */const getCurrentTimeFormatted=()=>getFormattedTimestamp(new Date());
439
444
 
445
+ const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
446
+ // eslint-disable-next-line func-names
447
+ return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
448
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
449
+ // @ts-ignore-next-line
450
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
451
+ * Utility method for JSON stringify object excluding null values & circular references
452
+ *
453
+ * @param {*} value input
454
+ * @param {boolean} excludeNull if it should exclude nul or not
455
+ * @param {function} logger optional logger methods for warning
456
+ * @returns string
457
+ */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};
458
+
440
459
  const MANUAL_ERROR_IDENTIFIER='[MANUAL ERROR]';/**
441
460
  * Get mutated error with issue prepended to error message
442
461
  * @param err Original error
@@ -444,7 +463,7 @@ const MANUAL_ERROR_IDENTIFIER='[MANUAL ERROR]';/**
444
463
  * @returns Instance of Error with message prepended with issue
445
464
  */const getMutatedError=(err,issue)=>{let finalError=err;if(!isTypeOfError(err)){finalError=new Error(`${issue}: ${stringifyWithoutCircular(err)}`);}else {finalError.message=`${issue}: ${err.message}`;}return finalError;};const dispatchErrorEvent=error=>{if(isTypeOfError(error)){error.stack=`${error.stack??''}\n${MANUAL_ERROR_IDENTIFIER}`;}globalThis.dispatchEvent(new ErrorEvent('error',{error}));};
446
465
 
447
- const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.6';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
466
+ const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.7';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
448
467
 
449
468
  const QUERY_PARAM_TRAIT_PREFIX='ajs_trait_';const QUERY_PARAM_PROPERTY_PREFIX='ajs_prop_';const QUERY_PARAM_ANONYMOUS_ID_KEY='ajs_aid';const QUERY_PARAM_USER_ID_KEY='ajs_uid';const QUERY_PARAM_TRACK_EVENT_NAME_KEY='ajs_event';
450
469
 
@@ -692,7 +711,7 @@ const removeDuplicateSlashes=str=>str.replace(/\/{2,}/g,'/');/**
692
711
  if(isFunction(globalThis.URL)){// eslint-disable-next-line no-new
693
712
  new URL(url);}return URL_PATTERN.test(url);}catch(e){return false;}};
694
713
 
695
- const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=details.xhr.status;// same as in v1.1
714
+ const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=getSanitizedValue(details.xhr).status;// same as in v1.1
696
715
  isRetryableNWFailure=xhrStatus===429||xhrStatus>=500&&xhrStatus<600;}return isRetryableNWFailure;};
697
716
 
698
717
  const userIdKey='rl_user_id';const userTraitsKey='rl_trait';const anonymousUserIdKey='rl_anonymous_id';const groupIdKey='rl_group_id';const groupTraitsKey='rl_group_trait';const pageInitialReferrerKey='rl_page_init_referrer';const pageInitialReferringDomainKey='rl_page_init_referring_domain';const sessionInfoKey='rl_session';const authTokenKey='rl_auth_token';const COOKIE_KEYS={userId:userIdKey,userTraits:userTraitsKey,anonymousId:anonymousUserIdKey,groupId:groupIdKey,groupTraits:groupTraitsKey,initialReferrer:pageInitialReferrerKey,initialReferringDomain:pageInitialReferringDomainKey,sessionInfo:sessionInfoKey,authToken:authTokenKey};const ENCRYPTION_PREFIX_V3='RS_ENC_v3_';
@@ -269,6 +269,10 @@ const isFunction=value=>typeof value==='function'&&Boolean(value.constructor&&va
269
269
  * @param value input value
270
270
  * @returns boolean
271
271
  */const isNullOrUndefined=value=>isNull(value)||isUndefined(value);/**
272
+ * Checks if the input is a BigInt
273
+ * @param value input value
274
+ * @returns True if the input is a BigInt
275
+ */const isBigInt=value=>typeof value==='bigint';/**
272
276
  * A function to check given value is defined
273
277
  * @param value input value
274
278
  * @returns boolean
@@ -286,6 +290,8 @@ const isFunction=value=>typeof value==='function'&&Boolean(value.constructor&&va
286
290
  * @returns true if the input is an instance of Error and false otherwise
287
291
  */const isTypeOfError=obj=>obj instanceof Error;
288
292
 
293
+ const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
294
+
289
295
  const getValueByPath=(obj,keyPath)=>{const pathParts=keyPath.split('.');return path(pathParts,obj);};const hasValueByPath=(obj,path)=>Boolean(getValueByPath(obj,path));const isObject=value=>typeof value==='object';/**
290
296
  * Checks if the input is an object literal or built-in object type and not null
291
297
  * @param value Input value
@@ -307,7 +313,28 @@ mergeDeepRight(mergedArray[index],value):value;});return mergedArray;};const mer
307
313
  * A utility to recursively remove undefined and null values from an object
308
314
  * @param obj input object
309
315
  * @returns a new object
310
- */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};
316
+ */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};const getReplacer=logger=>{const ancestors=[];// Array to track ancestor objects
317
+ // Using a regular function to use `this` for the parent context
318
+ return function replacer(key,value){if(isBigInt(value)){return '[BigInt]';// Replace BigInt values
319
+ }// `this` is the object that value is contained in, i.e., its direct parent.
320
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
321
+ // @ts-ignore-next-line
322
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();// Remove ancestors that are no longer part of the chain
323
+ }// Check for circular references (if the value is already in the ancestors)
324
+ if(ancestors.includes(value)){return '[Circular Reference]';}// Add current value to ancestors
325
+ ancestors.push(value);return value;};};const traverseWithThis=(obj,replacer)=>{// Create a new result object or array
326
+ const result=Array.isArray(obj)?[]:{};// Traverse object properties or array elements
327
+ // eslint-disable-next-line no-restricted-syntax
328
+ for(const key in obj){if(Object.hasOwnProperty.call(obj,key)){const value=obj[key];// Recursively apply the replacer and traversal
329
+ const sanitizedValue=replacer.call(obj,key,value);// If the value is an object or array, continue traversal
330
+ if(isObjectLiteralAndNotNull(sanitizedValue)||Array.isArray(sanitizedValue)){result[key]=traverseWithThis(sanitizedValue,replacer);}else {result[key]=sanitizedValue;}}}return result;};/**
331
+ * Recursively traverses an object similar to JSON.stringify,
332
+ * sanitizing BigInts and circular references
333
+ * @param value Input object
334
+ * @param logger Logger instance
335
+ * @returns Sanitized value
336
+ */const getSanitizedValue=(value,logger)=>{const replacer=getReplacer();// This is needed for registering the first ancestor
337
+ const newValue=replacer.call(value,'',value);if(isObjectLiteralAndNotNull(value)||Array.isArray(value)){return traverseWithThis(value,replacer);}return newValue;};
311
338
 
312
339
  const trim=value=>value.replace(/^\s+|\s+$/gm,'');const removeDoubleSpaces=value=>value.replace(/ {2,}/g,' ');const removeLeadingPeriod=value=>value.replace(/^\.+/,'');/**
313
340
  * A function to convert values to string
@@ -333,59 +360,37 @@ const trim=value=>value.replace(/^\s+|\s+$/gm,'');const removeDoubleSpaces=value
333
360
  * @returns decoded string
334
361
  */const fromBase64=value=>new TextDecoder().decode(base64ToBytes(value));
335
362
 
336
- const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
337
-
338
- const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
339
- // eslint-disable-next-line func-names
340
- return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
341
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
342
- // @ts-ignore-next-line
343
- while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
344
- * Utility method for JSON stringify object excluding null values & circular references
345
- *
346
- * @param {*} value input
347
- * @param {boolean} excludeNull if it should exclude nul or not
348
- * @param {function} logger optional logger methods for warning
349
- * @returns string
350
- */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};/**
351
- * Recursively traverses an object similar to JSON.stringify,
352
- * sanitizing BigInts and circular references
353
- * @param value Input object
354
- * @param logger Logger instance
355
- * @returns Sanitized value
356
- */const getSanitizedValue=(value,logger)=>value;
357
-
358
363
  // if yes make them null instead of omitting in overloaded cases
359
364
  /*
360
365
  * Normalise the overloaded arguments of the page call facade
361
- */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const sanitizedCategory=getSanitizedValue(category);const sanitizedName=getSanitizedValue(name);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={category:sanitizedCategory,name:sanitizedName,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}if(isFunction(sanitizedName)){payload.category=sanitizedCategory;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedName;}if(isFunction(sanitizedCategory)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedCategory;}if(isObjectLiteralAndNotNull(sanitizedCategory)){payload.name=undefined;payload.category=undefined;payload.properties=sanitizedCategory;if(!isFunction(sanitizedName)){payload.options=sanitizedName;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(sanitizedName)){payload.name=undefined;payload.properties=sanitizedName;if(!isFunction(sanitizedProperties)){payload.options=sanitizedProperties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
366
+ */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const payload={category:category,name:name,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.category=category;payload.name=name;payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.category=category;payload.name=name;payload.properties=undefined;payload.options=undefined;payload.callback=properties;}if(isFunction(name)){payload.category=category;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=name;}if(isFunction(category)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=category;}if(isObjectLiteralAndNotNull(category)){payload.name=undefined;payload.category=undefined;payload.properties=category;if(!isFunction(name)){payload.options=name;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(name)){payload.name=undefined;payload.properties=name;if(!isFunction(properties)){payload.options=properties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
362
367
  // use it as name and set category to undefined
363
- if(isString(sanitizedCategory)&&!isString(sanitizedName)){payload.category=undefined;payload.name=sanitizedCategory;}// Rest of the code is just to clean up undefined values
368
+ if(isString(category)&&!isString(name)){payload.category=undefined;payload.name=category;}// Rest of the code is just to clean up undefined values
364
369
  // and set some proper defaults
365
370
  // Also, to clone the incoming object type arguments
366
371
  if(!isDefined(payload.category)){payload.category=undefined;}if(!isDefined(payload.name)){payload.name=undefined;}payload.properties=payload.properties?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}const nameForProperties=isString(payload.name)?payload.name:payload.properties.name;const categoryForProperties=isString(payload.category)?payload.category:payload.properties.category;// add name and category to properties
367
372
  payload.properties=mergeDeepRight(isObjectLiteralAndNotNull(payload.properties)?payload.properties:{},{...(nameForProperties&&{name:nameForProperties}),...(categoryForProperties&&{category:categoryForProperties})});return payload;};/*
368
373
  * Normalise the overloaded arguments of the track call facade
369
- */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const sanitizedEvent=getSanitizedValue(event);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={name:sanitizedEvent,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}// Rest of the code is just to clean up undefined values
374
+ */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const payload={name:event,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.properties=undefined;payload.options=undefined;payload.callback=properties;}// Rest of the code is just to clean up undefined values
370
375
  // and set some proper defaults
371
376
  // Also, to clone the incoming object type arguments
372
377
  payload.properties=isDefinedAndNotNull(payload.properties)?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
373
378
  * Normalise the overloaded arguments of the identify call facade
374
- */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const sanitizedUserId=getSanitizedValue(userId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={userId:sanitizedUserId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.userId=sanitizedUserId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.userId=sanitizedUserId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedUserId)||isNull(sanitizedUserId)){// Explicitly set null to prevent resetting the existing value
379
+ */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const payload={userId:userId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.userId=userId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.userId=userId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(userId)||isNull(userId)){// Explicitly set null to prevent resetting the existing value
375
380
  // in the Analytics class
376
- payload.userId=null;payload.traits=sanitizedUserId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
381
+ payload.userId=null;payload.traits=userId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
377
382
  // and set some proper defaults
378
383
  // Also, to clone the incoming object type arguments
379
384
  payload.userId=tryStringify(payload.userId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
380
385
  * Normalise the overloaded arguments of the alias call facade
381
- */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const sanitizedTo=getSanitizedValue(to);const sanitizedFrom=getSanitizedValue(from);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={to:sanitizedTo,from:sanitizedFrom,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.to=sanitizedTo;payload.from=sanitizedFrom;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=undefined;payload.callback=sanitizedFrom;}else if(isObjectLiteralAndNotNull(sanitizedFrom)||isNull(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=sanitizedFrom;}// Rest of the code is just to clean up undefined values
386
+ */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const payload={to,from:from,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.to=to;payload.from=from;payload.options=undefined;payload.callback=options;}if(isFunction(from)){payload.to=to;payload.from=undefined;payload.options=undefined;payload.callback=from;}else if(isObjectLiteralAndNotNull(from)||isNull(from)){payload.to=to;payload.from=undefined;payload.options=from;}// Rest of the code is just to clean up undefined values
382
387
  // and set some proper defaults
383
388
  // Also, to clone the incoming object type arguments
384
389
  if(isDefined(payload.to)){payload.to=tryStringify(payload.to);}if(isDefined(payload.from)){payload.from=tryStringify(payload.from);}else {payload.from=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
385
390
  * Normalise the overloaded arguments of the group call facade
386
- */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const sanitizedGroupId=getSanitizedValue(groupId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={groupId:sanitizedGroupId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.groupId=sanitizedGroupId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.groupId=sanitizedGroupId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedGroupId)||isNull(sanitizedGroupId)){// Explicitly set null to prevent resetting the existing value
391
+ */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const payload={groupId:groupId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.groupId=groupId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.groupId=groupId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(groupId)||isNull(groupId)){// Explicitly set null to prevent resetting the existing value
387
392
  // in the Analytics class
388
- payload.groupId=null;payload.traits=sanitizedGroupId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
393
+ payload.groupId=null;payload.traits=groupId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
389
394
  // and set some proper defaults
390
395
  // Also, to clone the incoming object type arguments
391
396
  payload.groupId=tryStringify(payload.groupId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};
@@ -433,6 +438,20 @@ const getFormattedTimestamp=date=>date.toISOString();/**
433
438
  * @returns ISO formatted timestamp string
434
439
  */const getCurrentTimeFormatted=()=>getFormattedTimestamp(new Date());
435
440
 
441
+ const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
442
+ // eslint-disable-next-line func-names
443
+ return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
444
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
445
+ // @ts-ignore-next-line
446
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
447
+ * Utility method for JSON stringify object excluding null values & circular references
448
+ *
449
+ * @param {*} value input
450
+ * @param {boolean} excludeNull if it should exclude nul or not
451
+ * @param {function} logger optional logger methods for warning
452
+ * @returns string
453
+ */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};
454
+
436
455
  const MANUAL_ERROR_IDENTIFIER='[MANUAL ERROR]';/**
437
456
  * Get mutated error with issue prepended to error message
438
457
  * @param err Original error
@@ -440,7 +459,7 @@ const MANUAL_ERROR_IDENTIFIER='[MANUAL ERROR]';/**
440
459
  * @returns Instance of Error with message prepended with issue
441
460
  */const getMutatedError=(err,issue)=>{let finalError=err;if(!isTypeOfError(err)){finalError=new Error(`${issue}: ${stringifyWithoutCircular(err)}`);}else {finalError.message=`${issue}: ${err.message}`;}return finalError;};const dispatchErrorEvent=error=>{if(isTypeOfError(error)){error.stack=`${error.stack??''}\n${MANUAL_ERROR_IDENTIFIER}`;}globalThis.dispatchEvent(new ErrorEvent('error',{error}));};
442
461
 
443
- const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.6';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
462
+ const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.7';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
444
463
 
445
464
  const QUERY_PARAM_TRAIT_PREFIX='ajs_trait_';const QUERY_PARAM_PROPERTY_PREFIX='ajs_prop_';const QUERY_PARAM_ANONYMOUS_ID_KEY='ajs_aid';const QUERY_PARAM_USER_ID_KEY='ajs_uid';const QUERY_PARAM_TRACK_EVENT_NAME_KEY='ajs_event';
446
465
 
@@ -688,7 +707,7 @@ const removeDuplicateSlashes=str=>str.replace(/\/{2,}/g,'/');/**
688
707
  if(isFunction(globalThis.URL)){// eslint-disable-next-line no-new
689
708
  new URL(url);}return URL_PATTERN.test(url);}catch(e){return false;}};
690
709
 
691
- const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=details.xhr.status;// same as in v1.1
710
+ const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=getSanitizedValue(details.xhr).status;// same as in v1.1
692
711
  isRetryableNWFailure=xhrStatus===429||xhrStatus>=500&&xhrStatus<600;}return isRetryableNWFailure;};
693
712
 
694
713
  const userIdKey='rl_user_id';const userTraitsKey='rl_trait';const anonymousUserIdKey='rl_anonymous_id';const groupIdKey='rl_group_id';const groupTraitsKey='rl_group_trait';const pageInitialReferrerKey='rl_page_init_referrer';const pageInitialReferringDomainKey='rl_page_init_referring_domain';const sessionInfoKey='rl_session';const authTokenKey='rl_auth_token';const COOKIE_KEYS={userId:userIdKey,userTraits:userTraitsKey,anonymousId:anonymousUserIdKey,groupId:groupIdKey,groupTraits:groupTraitsKey,initialReferrer:pageInitialReferrerKey,initialReferringDomain:pageInitialReferringDomainKey,sessionInfo:sessionInfoKey,authToken:authTokenKey};const ENCRYPTION_PREFIX_V3='RS_ENC_v3_';
@@ -275,6 +275,10 @@
275
275
  * @param value input value
276
276
  * @returns boolean
277
277
  */const isNullOrUndefined=value=>isNull(value)||isUndefined(value);/**
278
+ * Checks if the input is a BigInt
279
+ * @param value input value
280
+ * @returns True if the input is a BigInt
281
+ */const isBigInt=value=>typeof value==='bigint';/**
278
282
  * A function to check given value is defined
279
283
  * @param value input value
280
284
  * @returns boolean
@@ -292,6 +296,8 @@
292
296
  * @returns true if the input is an instance of Error and false otherwise
293
297
  */const isTypeOfError=obj=>obj instanceof Error;
294
298
 
299
+ const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
300
+
295
301
  const getValueByPath=(obj,keyPath)=>{const pathParts=keyPath.split('.');return path(pathParts,obj);};const hasValueByPath=(obj,path)=>Boolean(getValueByPath(obj,path));const isObject=value=>typeof value==='object';/**
296
302
  * Checks if the input is an object literal or built-in object type and not null
297
303
  * @param value Input value
@@ -313,7 +319,28 @@
313
319
  * A utility to recursively remove undefined and null values from an object
314
320
  * @param obj input object
315
321
  * @returns a new object
316
- */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};
322
+ */const removeUndefinedAndNullValues=obj=>{const result=pickBy(isDefinedAndNotNull,obj);Object.keys(result).forEach(key=>{const value=result[key];if(isObjectLiteralAndNotNull(value)){result[key]=removeUndefinedAndNullValues(value);}});return result;};const getReplacer=logger=>{const ancestors=[];// Array to track ancestor objects
323
+ // Using a regular function to use `this` for the parent context
324
+ return function replacer(key,value){if(isBigInt(value)){return '[BigInt]';// Replace BigInt values
325
+ }// `this` is the object that value is contained in, i.e., its direct parent.
326
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
327
+ // @ts-ignore-next-line
328
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();// Remove ancestors that are no longer part of the chain
329
+ }// Check for circular references (if the value is already in the ancestors)
330
+ if(ancestors.includes(value)){return '[Circular Reference]';}// Add current value to ancestors
331
+ ancestors.push(value);return value;};};const traverseWithThis=(obj,replacer)=>{// Create a new result object or array
332
+ const result=Array.isArray(obj)?[]:{};// Traverse object properties or array elements
333
+ // eslint-disable-next-line no-restricted-syntax
334
+ for(const key in obj){if(Object.hasOwnProperty.call(obj,key)){const value=obj[key];// Recursively apply the replacer and traversal
335
+ const sanitizedValue=replacer.call(obj,key,value);// If the value is an object or array, continue traversal
336
+ if(isObjectLiteralAndNotNull(sanitizedValue)||Array.isArray(sanitizedValue)){result[key]=traverseWithThis(sanitizedValue,replacer);}else {result[key]=sanitizedValue;}}}return result;};/**
337
+ * Recursively traverses an object similar to JSON.stringify,
338
+ * sanitizing BigInts and circular references
339
+ * @param value Input object
340
+ * @param logger Logger instance
341
+ * @returns Sanitized value
342
+ */const getSanitizedValue=(value,logger)=>{const replacer=getReplacer();// This is needed for registering the first ancestor
343
+ const newValue=replacer.call(value,'',value);if(isObjectLiteralAndNotNull(value)||Array.isArray(value)){return traverseWithThis(value,replacer);}return newValue;};
317
344
 
318
345
  const trim=value=>value.replace(/^\s+|\s+$/gm,'');const removeDoubleSpaces=value=>value.replace(/ {2,}/g,' ');const removeLeadingPeriod=value=>value.replace(/^\.+/,'');/**
319
346
  * A function to convert values to string
@@ -339,59 +366,37 @@
339
366
  * @returns decoded string
340
367
  */const fromBase64=value=>new TextDecoder().decode(base64ToBytes(value));
341
368
 
342
- const LOG_CONTEXT_SEPARATOR=':: ';const SCRIPT_ALREADY_EXISTS_ERROR=id=>`A script with the id "${id}" is already loaded. Skipping the loading of this script to prevent conflicts.`;const SCRIPT_LOAD_ERROR=(id,url)=>`Failed to load the script with the id "${id}" from URL "${url}".`;const SCRIPT_LOAD_TIMEOUT_ERROR=(id,url,timeout)=>`A timeout of ${timeout} ms occurred while trying to load the script with id "${id}" from URL "${url}".`;const CIRCULAR_REFERENCE_WARNING=(context,key)=>`${context}${LOG_CONTEXT_SEPARATOR}A circular reference has been detected in the object and the property "${key}" has been dropped from the output.`;const JSON_STRINGIFY_WARNING=`Failed to convert the value to a JSON string.`;
343
-
344
- const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
345
- // eslint-disable-next-line func-names
346
- return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
347
- // eslint-disable-next-line @typescript-eslint/ban-ts-comment
348
- // @ts-ignore-next-line
349
- while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
350
- * Utility method for JSON stringify object excluding null values & circular references
351
- *
352
- * @param {*} value input
353
- * @param {boolean} excludeNull if it should exclude nul or not
354
- * @param {function} logger optional logger methods for warning
355
- * @returns string
356
- */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};/**
357
- * Recursively traverses an object similar to JSON.stringify,
358
- * sanitizing BigInts and circular references
359
- * @param value Input object
360
- * @param logger Logger instance
361
- * @returns Sanitized value
362
- */const getSanitizedValue=(value,logger)=>value;
363
-
364
369
  // if yes make them null instead of omitting in overloaded cases
365
370
  /*
366
371
  * Normalise the overloaded arguments of the page call facade
367
- */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const sanitizedCategory=getSanitizedValue(category);const sanitizedName=getSanitizedValue(name);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={category:sanitizedCategory,name:sanitizedName,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.category=sanitizedCategory;payload.name=sanitizedName;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}if(isFunction(sanitizedName)){payload.category=sanitizedCategory;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedName;}if(isFunction(sanitizedCategory)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedCategory;}if(isObjectLiteralAndNotNull(sanitizedCategory)){payload.name=undefined;payload.category=undefined;payload.properties=sanitizedCategory;if(!isFunction(sanitizedName)){payload.options=sanitizedName;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(sanitizedName)){payload.name=undefined;payload.properties=sanitizedName;if(!isFunction(sanitizedProperties)){payload.options=sanitizedProperties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
372
+ */const pageArgumentsToCallOptions=(category,name,properties,options,callback)=>{const payload={category:category,name:name,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.category=category;payload.name=name;payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.category=category;payload.name=name;payload.properties=undefined;payload.options=undefined;payload.callback=properties;}if(isFunction(name)){payload.category=category;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=name;}if(isFunction(category)){payload.category=undefined;payload.name=undefined;payload.properties=undefined;payload.options=undefined;payload.callback=category;}if(isObjectLiteralAndNotNull(category)){payload.name=undefined;payload.category=undefined;payload.properties=category;if(!isFunction(name)){payload.options=name;}else {payload.options=undefined;}}else if(isObjectLiteralAndNotNull(name)){payload.name=undefined;payload.properties=name;if(!isFunction(properties)){payload.options=properties;}else {payload.options=undefined;}}// if the category argument alone is provided b/w category and name,
368
373
  // use it as name and set category to undefined
369
- if(isString(sanitizedCategory)&&!isString(sanitizedName)){payload.category=undefined;payload.name=sanitizedCategory;}// Rest of the code is just to clean up undefined values
374
+ if(isString(category)&&!isString(name)){payload.category=undefined;payload.name=category;}// Rest of the code is just to clean up undefined values
370
375
  // and set some proper defaults
371
376
  // Also, to clone the incoming object type arguments
372
377
  if(!isDefined(payload.category)){payload.category=undefined;}if(!isDefined(payload.name)){payload.name=undefined;}payload.properties=payload.properties?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}const nameForProperties=isString(payload.name)?payload.name:payload.properties.name;const categoryForProperties=isString(payload.category)?payload.category:payload.properties.category;// add name and category to properties
373
378
  payload.properties=mergeDeepRight(isObjectLiteralAndNotNull(payload.properties)?payload.properties:{},{...(nameForProperties&&{name:nameForProperties}),...(categoryForProperties&&{category:categoryForProperties})});return payload;};/*
374
379
  * Normalise the overloaded arguments of the track call facade
375
- */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const sanitizedEvent=getSanitizedValue(event);const sanitizedProperties=getSanitizedValue(properties);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={name:sanitizedEvent,properties:sanitizedProperties,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.properties=sanitizedProperties;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedProperties)){payload.properties=undefined;payload.options=undefined;payload.callback=sanitizedProperties;}// Rest of the code is just to clean up undefined values
380
+ */const trackArgumentsToCallOptions=(event,properties,options,callback)=>{const payload={name:event,properties:properties,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.properties=properties;payload.options=undefined;payload.callback=options;}if(isFunction(properties)){payload.properties=undefined;payload.options=undefined;payload.callback=properties;}// Rest of the code is just to clean up undefined values
376
381
  // and set some proper defaults
377
382
  // Also, to clone the incoming object type arguments
378
383
  payload.properties=isDefinedAndNotNull(payload.properties)?clone(payload.properties):{};if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
379
384
  * Normalise the overloaded arguments of the identify call facade
380
- */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const sanitizedUserId=getSanitizedValue(userId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={userId:sanitizedUserId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.userId=sanitizedUserId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.userId=sanitizedUserId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedUserId)||isNull(sanitizedUserId)){// Explicitly set null to prevent resetting the existing value
385
+ */const identifyArgumentsToCallOptions=(userId,traits,options,callback)=>{const payload={userId:userId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.userId=userId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.userId=userId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(userId)||isNull(userId)){// Explicitly set null to prevent resetting the existing value
381
386
  // in the Analytics class
382
- payload.userId=null;payload.traits=sanitizedUserId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
387
+ payload.userId=null;payload.traits=userId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
383
388
  // and set some proper defaults
384
389
  // Also, to clone the incoming object type arguments
385
390
  payload.userId=tryStringify(payload.userId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
386
391
  * Normalise the overloaded arguments of the alias call facade
387
- */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const sanitizedTo=getSanitizedValue(to);const sanitizedFrom=getSanitizedValue(from);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={to:sanitizedTo,from:sanitizedFrom,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.to=sanitizedTo;payload.from=sanitizedFrom;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=undefined;payload.callback=sanitizedFrom;}else if(isObjectLiteralAndNotNull(sanitizedFrom)||isNull(sanitizedFrom)){payload.to=sanitizedTo;payload.from=undefined;payload.options=sanitizedFrom;}// Rest of the code is just to clean up undefined values
392
+ */const aliasArgumentsToCallOptions=(to,from,options,callback)=>{const payload={to,from:from,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.to=to;payload.from=from;payload.options=undefined;payload.callback=options;}if(isFunction(from)){payload.to=to;payload.from=undefined;payload.options=undefined;payload.callback=from;}else if(isObjectLiteralAndNotNull(from)||isNull(from)){payload.to=to;payload.from=undefined;payload.options=from;}// Rest of the code is just to clean up undefined values
388
393
  // and set some proper defaults
389
394
  // Also, to clone the incoming object type arguments
390
395
  if(isDefined(payload.to)){payload.to=tryStringify(payload.to);}if(isDefined(payload.from)){payload.from=tryStringify(payload.from);}else {payload.from=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};/*
391
396
  * Normalise the overloaded arguments of the group call facade
392
- */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const sanitizedGroupId=getSanitizedValue(groupId);const sanitizedTraits=getSanitizedValue(traits);const sanitizedOptions=getSanitizedValue(options);const sanitizedCallback=getSanitizedValue(callback);const payload={groupId:sanitizedGroupId,traits:sanitizedTraits,options:sanitizedOptions,callback:undefined};if(isFunction(sanitizedCallback)){payload.callback=sanitizedCallback;}if(isFunction(sanitizedOptions)){payload.groupId=sanitizedGroupId;payload.traits=sanitizedTraits;payload.options=undefined;payload.callback=sanitizedOptions;}if(isFunction(sanitizedTraits)){payload.groupId=sanitizedGroupId;payload.traits=undefined;payload.options=undefined;payload.callback=sanitizedTraits;}if(isObjectLiteralAndNotNull(sanitizedGroupId)||isNull(sanitizedGroupId)){// Explicitly set null to prevent resetting the existing value
397
+ */const groupArgumentsToCallOptions=(groupId,traits,options,callback)=>{const payload={groupId:groupId,traits:traits,options:options,callback:undefined};if(isFunction(callback)){payload.callback=callback;}if(isFunction(options)){payload.groupId=groupId;payload.traits=traits;payload.options=undefined;payload.callback=options;}if(isFunction(traits)){payload.groupId=groupId;payload.traits=undefined;payload.options=undefined;payload.callback=traits;}if(isObjectLiteralAndNotNull(groupId)||isNull(groupId)){// Explicitly set null to prevent resetting the existing value
393
398
  // in the Analytics class
394
- payload.groupId=null;payload.traits=sanitizedGroupId;if(!isFunction(sanitizedTraits)){payload.options=sanitizedTraits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
399
+ payload.groupId=null;payload.traits=groupId;if(!isFunction(traits)){payload.options=traits;}else {payload.options=undefined;}}// Rest of the code is just to clean up undefined values
395
400
  // and set some proper defaults
396
401
  // Also, to clone the incoming object type arguments
397
402
  payload.groupId=tryStringify(payload.groupId);if(isObjectLiteralAndNotNull(payload.traits)){payload.traits=clone(payload.traits);}else {payload.traits=undefined;}if(isDefined(payload.options)){payload.options=clone(payload.options);}else {payload.options=undefined;}return payload;};
@@ -439,6 +444,20 @@
439
444
  * @returns ISO formatted timestamp string
440
445
  */const getCurrentTimeFormatted=()=>getFormattedTimestamp(new Date());
441
446
 
447
+ const JSON_STRINGIFY='JSONStringify';const getCircularReplacer=(excludeNull,excludeKeys,logger)=>{const ancestors=[];// Here we do not want to use arrow function to use "this" in function context
448
+ // eslint-disable-next-line func-names
449
+ return function(key,value){if(excludeKeys?.includes(key)){return undefined;}if(excludeNull&&isNullOrUndefined(value)){return undefined;}if(typeof value!=='object'||isNull(value)){return value;}// `this` is the object that value is contained in, i.e., its direct parent.
450
+ // eslint-disable-next-line @typescript-eslint/ban-ts-comment
451
+ // @ts-ignore-next-line
452
+ while(ancestors.length>0&&ancestors[ancestors.length-1]!==this){ancestors.pop();}if(ancestors.includes(value)){logger?.warn(CIRCULAR_REFERENCE_WARNING(JSON_STRINGIFY,key));return '[Circular Reference]';}ancestors.push(value);return value;};};/**
453
+ * Utility method for JSON stringify object excluding null values & circular references
454
+ *
455
+ * @param {*} value input
456
+ * @param {boolean} excludeNull if it should exclude nul or not
457
+ * @param {function} logger optional logger methods for warning
458
+ * @returns string
459
+ */const stringifyWithoutCircular=(value,excludeNull,excludeKeys,logger)=>{try{return JSON.stringify(value,getCircularReplacer(excludeNull,excludeKeys,logger));}catch(err){logger?.warn(JSON_STRINGIFY_WARNING,err);return null;}};
460
+
442
461
  const MANUAL_ERROR_IDENTIFIER='[MANUAL ERROR]';/**
443
462
  * Get mutated error with issue prepended to error message
444
463
  * @param err Original error
@@ -446,7 +465,7 @@
446
465
  * @returns Instance of Error with message prepended with issue
447
466
  */const getMutatedError=(err,issue)=>{let finalError=err;if(!isTypeOfError(err)){finalError=new Error(`${issue}: ${stringifyWithoutCircular(err)}`);}else {finalError.message=`${issue}: ${err.message}`;}return finalError;};const dispatchErrorEvent=error=>{if(isTypeOfError(error)){error.stack=`${error.stack??''}\n${MANUAL_ERROR_IDENTIFIER}`;}globalThis.dispatchEvent(new ErrorEvent('error',{error}));};
448
467
 
449
- const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.6';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
468
+ const APP_NAME='RudderLabs JavaScript SDK';const APP_VERSION='3.11.7';const APP_NAMESPACE='com.rudderlabs.javascript';const MODULE_TYPE='npm';const ADBLOCK_PAGE_CATEGORY='RudderJS-Initiated';const ADBLOCK_PAGE_NAME='ad-block page request';const ADBLOCK_PAGE_PATH='/ad-blocked';const GLOBAL_PRELOAD_BUFFER='preloadedEventsBuffer';const CONSENT_TRACK_EVENT_NAME='Consent Management Interaction';
450
469
 
451
470
  const QUERY_PARAM_TRAIT_PREFIX='ajs_trait_';const QUERY_PARAM_PROPERTY_PREFIX='ajs_prop_';const QUERY_PARAM_ANONYMOUS_ID_KEY='ajs_aid';const QUERY_PARAM_USER_ID_KEY='ajs_uid';const QUERY_PARAM_TRACK_EVENT_NAME_KEY='ajs_event';
452
471
 
@@ -694,7 +713,7 @@
694
713
  if(isFunction(globalThis.URL)){// eslint-disable-next-line no-new
695
714
  new URL(url);}return URL_PATTERN.test(url);}catch(e){return false;}};
696
715
 
697
- const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=details.xhr.status;// same as in v1.1
716
+ const isErrRetryable=details=>{let isRetryableNWFailure=false;if(details?.error&&details?.xhr){const xhrStatus=getSanitizedValue(details.xhr).status;// same as in v1.1
698
717
  isRetryableNWFailure=xhrStatus===429||xhrStatus>=500&&xhrStatus<600;}return isRetryableNWFailure;};
699
718
 
700
719
  const userIdKey='rl_user_id';const userTraitsKey='rl_trait';const anonymousUserIdKey='rl_anonymous_id';const groupIdKey='rl_group_id';const groupTraitsKey='rl_group_trait';const pageInitialReferrerKey='rl_page_init_referrer';const pageInitialReferringDomainKey='rl_page_init_referring_domain';const sessionInfoKey='rl_session';const authTokenKey='rl_auth_token';const COOKIE_KEYS={userId:userIdKey,userTraits:userTraitsKey,anonymousId:anonymousUserIdKey,groupId:groupIdKey,groupTraits:groupTraitsKey,initialReferrer:pageInitialReferrerKey,initialReferringDomain:pageInitialReferringDomainKey,sessionInfo:sessionInfoKey,authToken:authTokenKey};const ENCRYPTION_PREFIX_V3='RS_ENC_v3_';