Skip to content

Commit

Permalink
fix(bigint): Use typeof for testing if BigInt exists
Browse files Browse the repository at this point in the history
The `if (BigInt) { … }` style does not work in browser environments that do not implement BigInt (e.g. Safari <= 13).

A `hasBigInt` flag was added and exported from `util` and uses the format of `typeof BigInt !== ‘undefined’` which should work in all environments.  All usage of `BigInt` is now guarded by an equivalent of `if (hasBigInt) {…}` to ensure it’s available before use.
  • Loading branch information
kdubb committed Jul 23, 2020
1 parent adb7bd3 commit ddeb3b5
Show file tree
Hide file tree
Showing 3 changed files with 16 additions and 9 deletions.
11 changes: 6 additions & 5 deletions src/core/JsonParser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
getDefaultPrimitiveTypeValue,
getMetadata,
getMetadataKeys,
hasBigInt,
hasMetadata,
isClassIterable,
isConstructorPrimitiveType,
Expand Down Expand Up @@ -284,7 +285,7 @@ export class JsonParser<T> {
if (value.constructor === String) {
if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, Number)) {
value = +value;
} else if (BigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
} else if (hasBigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
value = BigInt(+value);
} else if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, Boolean)) {
if (value.toLowerCase() === 'true' || value === '1') {
Expand All @@ -298,7 +299,7 @@ export class JsonParser<T> {
} else if (value.constructor === Number) {
if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, Boolean)) {
value = !!value;
} else if (BigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
} else if (hasBigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
value = BigInt(+value);
} else if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, String)) {
// @ts-ignore
Expand All @@ -307,7 +308,7 @@ export class JsonParser<T> {
} else if (value.constructor === Boolean) {
if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, Number)) {
value = value ? 1 : 0;
} else if (BigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
} else if (hasBigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
value = BigInt(value ? 1 : 0);
} else if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, String)) {
// @ts-ignore
Expand Down Expand Up @@ -353,7 +354,7 @@ export class JsonParser<T> {
if (isSameConstructorOrExtensionOfNoObject(currentMainCreator, Map) ||
(typeof value === 'object' && !isIterableNoMapNoString(value) && currentMainCreator === Object)) {
return this.parseMapAndObjLiteral(key, value, context, globalContext);
} else if (BigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
} else if (hasBigInt && isSameConstructorOrExtensionOfNoObject(currentMainCreator, BigInt)) {
return (value != null && value.constructor === String && value.endsWith('n')) ?
// @ts-ignore
currentMainCreator(value.substring(0, value.length - 1)) :
Expand Down Expand Up @@ -459,7 +460,7 @@ export class JsonParser<T> {
(context.features.deserialization.SET_DEFAULT_VALUE_FOR_PRIMITIVES_ON_NULL ||
context.features.deserialization.SET_DEFAULT_VALUE_FOR_BOOLEAN_ON_NULL) ) {
defaultValue = getDefaultPrimitiveTypeValue(Boolean);
} else if (BigInt && currentMainCreator === BigInt &&
} else if (hasBigInt && currentMainCreator === BigInt &&
(context.features.deserialization.SET_DEFAULT_VALUE_FOR_PRIMITIVES_ON_NULL ||
context.features.deserialization.SET_DEFAULT_VALUE_FOR_BIGINT_ON_NULL) ) {
defaultValue = getDefaultPrimitiveTypeValue(BigInt);
Expand Down
5 changes: 3 additions & 2 deletions src/core/JsonStringifier.ts
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ import {
getDefaultValue,
getMetadata,
getObjectKeysWithPropertyDescriptorNames,
hasBigInt,
hasMetadata,
isConstructorPrimitiveType,
isIterableNoMapNoString,
Expand Down Expand Up @@ -337,7 +338,7 @@ export class JsonStringifier<T> {

value = this.stringifyJsonFormatClass(value, context);

if (BigInt && isSameConstructorOrExtensionOfNoObject(value.constructor, BigInt)) {
if (hasBigInt && isSameConstructorOrExtensionOfNoObject(value.constructor, BigInt)) {
return value.toString() + 'n';
} else if (value instanceof RegExp) {
const replacement = value.toString();
Expand Down Expand Up @@ -565,7 +566,7 @@ export class JsonStringifier<T> {
(context.features.serialization.SET_DEFAULT_VALUE_FOR_PRIMITIVES_ON_NULL ||
context.features.serialization.SET_DEFAULT_VALUE_FOR_BOOLEAN_ON_NULL) ) {
defaultValue = getDefaultPrimitiveTypeValue(Boolean);
} else if (BigInt && currentMainCreator === BigInt &&
} else if (hasBigInt && currentMainCreator === BigInt &&
(context.features.serialization.SET_DEFAULT_VALUE_FOR_PRIMITIVES_ON_NULL ||
context.features.serialization.SET_DEFAULT_VALUE_FOR_BIGINT_ON_NULL) ) {
defaultValue = getDefaultPrimitiveTypeValue(BigInt);
Expand Down
9 changes: 7 additions & 2 deletions src/util.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,11 @@ import {
DefaultContextGroup
} from './core/DefaultContextGroup';

/**
* Flag for testing if BigInt is supported
*/
export const hasBigInt = typeof BigInt !== 'undefined';

/**
* @internal
*/
Expand Down Expand Up @@ -824,7 +829,7 @@ export const isVariablePrimitiveType = (value: any): boolean => value != null &&
* @internal
*/
export const isConstructorPrimitiveType = (ctor: any): boolean => ctor === Number ||
(BigInt && ctor === BigInt) || ctor === String ||
(hasBigInt && ctor === BigInt) || ctor === String ||
ctor === Boolean || (Symbol && ctor === Symbol);

/**
Expand All @@ -839,7 +844,7 @@ export const getDefaultPrimitiveTypeValue = (ctor: ClassType<any>): any | null =
case String:
return '';
default:
if (BigInt && ctor === BigInt) {
if (hasBigInt && ctor === BigInt) {
return BigInt(0);
}
}
Expand Down

0 comments on commit ddeb3b5

Please sign in to comment.