From cb86500955ed71b62a45175591fd5a26089bdcfb Mon Sep 17 00:00:00 2001 From: Christian Baroni <7061887+christianbaroni@users.noreply.github.com> Date: Mon, 27 May 2024 18:45:44 +0000 Subject: [PATCH 1/2] Fix negative number support, add number comparison functions --- src/__swaps__/safe-math/SafeMath.ts | 89 +++++++++++++++++-- .../safe-math/__tests__/SafeMath.test.ts | 78 +++++++++++++++- 2 files changed, 161 insertions(+), 6 deletions(-) diff --git a/src/__swaps__/safe-math/SafeMath.ts b/src/__swaps__/safe-math/SafeMath.ts index 017ed7a22b2..e6f68d487d2 100644 --- a/src/__swaps__/safe-math/SafeMath.ts +++ b/src/__swaps__/safe-math/SafeMath.ts @@ -1,5 +1,6 @@ // Utility function to remove the decimal point and keep track of the number of decimal places const removeDecimal = (num: string): [bigint, number] => { + 'worklet'; const parts = num.split('.'); const decimalPlaces = parts.length === 2 ? parts[1].length : 0; const bigIntNum = BigInt(parts.join('')); @@ -7,10 +8,12 @@ const removeDecimal = (num: string): [bigint, number] => { }; const isNumberString = (value: string): boolean => { - return /^\d+(\.\d+)?$/.test(value); + 'worklet'; + return /^-?\d+(\.\d+)?$/.test(value); }; const isZero = (value: string): boolean => { + 'worklet'; if (parseFloat(value) === 0) { return true; } @@ -19,21 +22,27 @@ const isZero = (value: string): boolean => { // Utility function to scale the number up to 20 decimal places const scaleUp = (bigIntNum: bigint, decimalPlaces: number): bigint => { - const scaleFactor = BigInt(10) ** (BigInt(20) - BigInt(decimalPlaces)); - return bigIntNum * scaleFactor; + 'worklet'; + const scaleFactor = BigInt(10) ** BigInt(20); + return (bigIntNum * scaleFactor) / BigInt(10) ** BigInt(decimalPlaces); }; // Utility function to format the result with 20 decimal places and remove trailing zeros const formatResult = (result: bigint): string => { - const resultStr = result.toString().padStart(21, '0'); // 20 decimal places + at least 1 integer place + 'worklet'; + const isNegative = result < 0; + const absResult = isNegative ? -result : result; + const resultStr = absResult.toString().padStart(21, '0'); // 20 decimal places + at least 1 integer place const integerPart = resultStr.slice(0, -20) || '0'; let fractionalPart = resultStr.slice(-20); fractionalPart = fractionalPart.replace(/0+$/, ''); // Remove trailing zeros - return fractionalPart.length > 0 ? `${integerPart}.${fractionalPart}` : integerPart; + const formattedResult = fractionalPart.length > 0 ? `${integerPart}.${fractionalPart}` : integerPart; + return isNegative ? `-${formattedResult}` : formattedResult; }; // Sum function export function sum(num1: string, num2: string): string { + 'worklet'; if (!isNumberString(num1) || !isNumberString(num2)) { throw new Error('Arguments must be a numeric string'); } @@ -54,6 +63,7 @@ export function sum(num1: string, num2: string): string { // Subtract function export function sub(num1: string, num2: string): string { + 'worklet'; if (!isNumberString(num1) || !isNumberString(num2)) { throw new Error('Arguments must be a numeric string'); } @@ -72,6 +82,7 @@ export function sub(num1: string, num2: string): string { // Multiply function export function mul(num1: string, num2: string): string { + 'worklet'; if (!isNumberString(num1) || !isNumberString(num2)) { throw new Error('Arguments must be a numeric string'); } @@ -88,6 +99,7 @@ export function mul(num1: string, num2: string): string { // Divide function export function div(num1: string, num2: string): string { + 'worklet'; if (!isNumberString(num1) || !isNumberString(num2)) { throw new Error('Arguments must be a numeric string'); } @@ -107,6 +119,7 @@ export function div(num1: string, num2: string): string { // Modulus function export function mod(num1: string, num2: string): string { + 'worklet'; if (!isNumberString(num1) || !isNumberString(num2)) { throw new Error('Arguments must be a numeric string'); } @@ -126,6 +139,7 @@ export function mod(num1: string, num2: string): string { // Power function export function pow(base: string, exponent: string): string { + 'worklet'; if (!isNumberString(base) || !isNumberString(exponent)) { throw new Error('Arguments must be a numeric string'); } @@ -140,3 +154,68 @@ export function pow(base: string, exponent: string): string { const result = scaledBigIntBase ** BigInt(exponent) / BigInt(10) ** BigInt(20); return formatResult(result); } + +// Equality function +export function equal(num1: string, num2: string): boolean { + 'worklet'; + if (!isNumberString(num1) || !isNumberString(num2)) { + throw new Error('Arguments must be a numeric string'); + } + const [bigInt1, decimalPlaces1] = removeDecimal(num1); + const [bigInt2, decimalPlaces2] = removeDecimal(num2); + const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + return scaledBigInt1 === scaledBigInt2; +} + +// Greater than function +export function greaterThan(num1: string, num2: string): boolean { + 'worklet'; + if (!isNumberString(num1) || !isNumberString(num2)) { + throw new Error('Arguments must be a numeric string'); + } + const [bigInt1, decimalPlaces1] = removeDecimal(num1); + const [bigInt2, decimalPlaces2] = removeDecimal(num2); + const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + return scaledBigInt1 > scaledBigInt2; +} + +// Greater than or equal to function +export function greaterThanOrEqualTo(num1: string, num2: string): boolean { + 'worklet'; + if (!isNumberString(num1) || !isNumberString(num2)) { + throw new Error('Arguments must be a numeric string'); + } + const [bigInt1, decimalPlaces1] = removeDecimal(num1); + const [bigInt2, decimalPlaces2] = removeDecimal(num2); + const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + return scaledBigInt1 >= scaledBigInt2; +} + +// Less than function +export function lessThan(num1: string, num2: string): boolean { + 'worklet'; + if (!isNumberString(num1) || !isNumberString(num2)) { + throw new Error('Arguments must be a numeric string'); + } + const [bigInt1, decimalPlaces1] = removeDecimal(num1); + const [bigInt2, decimalPlaces2] = removeDecimal(num2); + const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + return scaledBigInt1 < scaledBigInt2; +} + +// Less than or equal to function +export function lessThanOrEqualTo(num1: string, num2: string): boolean { + 'worklet'; + if (!isNumberString(num1) || !isNumberString(num2)) { + throw new Error('Arguments must be a numeric string'); + } + const [bigInt1, decimalPlaces1] = removeDecimal(num1); + const [bigInt2, decimalPlaces2] = removeDecimal(num2); + const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + return scaledBigInt1 <= scaledBigInt2; +} diff --git a/src/__swaps__/safe-math/__tests__/SafeMath.test.ts b/src/__swaps__/safe-math/__tests__/SafeMath.test.ts index ee2c4b55beb..94e487c5cf4 100644 --- a/src/__swaps__/safe-math/__tests__/SafeMath.test.ts +++ b/src/__swaps__/safe-math/__tests__/SafeMath.test.ts @@ -1,4 +1,4 @@ -import { sum, sub, mul, div, mod, pow } from '../SafeMath'; +import { sum, sub, mul, div, mod, pow, equal, greaterThan, greaterThanOrEqualTo, lessThan, lessThanOrEqualTo } from '../SafeMath'; import BigNumber from 'bignumber.js'; const RESULTS = { @@ -13,6 +13,7 @@ const RESULTS = { const VALUE_A = '1243425.345'; const VALUE_B = '3819.24'; const VALUE_C = '2'; +const NEGATIVE_VALUE = '-2412.12'; const ZERO = '0'; const ONE = '1'; const NON_NUMERIC_STRING = 'abc'; @@ -33,6 +34,7 @@ describe('SafeMath', () => { expect(sub(ZERO, ZERO)).toBe(ZERO); expect(sub(VALUE_A, ZERO)).toBe(VALUE_A); expect(sub(ZERO, VALUE_B)).toBe(`-${VALUE_B}`); + expect(sub(NEGATIVE_VALUE, ZERO)).toBe(NEGATIVE_VALUE); expect(sub(VALUE_A, VALUE_B)).toBe(RESULTS.sub); }); @@ -62,6 +64,7 @@ describe('SafeMath', () => { expect(mod(ZERO, VALUE_B)).toBe(ZERO); expect(mod(VALUE_A, VALUE_B)).toBe(RESULTS.mod); }); + test('pow', () => { expect(() => pow(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); expect(() => pow(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); @@ -70,6 +73,51 @@ describe('SafeMath', () => { expect(pow(ZERO, VALUE_B)).toBe(ZERO); expect(pow(VALUE_A, VALUE_C)).toBe(RESULTS.pow); }); + + test('equal', () => { + expect(() => equal(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => equal(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(equal(ZERO, ZERO)).toBe(true); + expect(equal(VALUE_A, VALUE_A)).toBe(true); + expect(equal(VALUE_A, VALUE_B)).toBe(false); + expect(equal(NEGATIVE_VALUE, NEGATIVE_VALUE)).toBe(true); + }); + + test('greaterThan', () => { + expect(() => greaterThan(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => greaterThan(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(greaterThan(VALUE_A, VALUE_B)).toBe(true); + expect(greaterThan(VALUE_B, VALUE_A)).toBe(false); + expect(greaterThan(VALUE_A, VALUE_A)).toBe(false); + expect(greaterThan(NEGATIVE_VALUE, VALUE_A)).toBe(false); + }); + + test('greaterThanOrEqualTo', () => { + expect(() => greaterThanOrEqualTo(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => greaterThanOrEqualTo(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(greaterThanOrEqualTo(VALUE_A, VALUE_B)).toBe(true); + expect(greaterThanOrEqualTo(VALUE_B, VALUE_A)).toBe(false); + expect(greaterThanOrEqualTo(VALUE_A, VALUE_A)).toBe(true); + expect(greaterThanOrEqualTo(NEGATIVE_VALUE, VALUE_A)).toBe(false); + }); + + test('lessThan', () => { + expect(() => lessThan(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => lessThan(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(lessThan(VALUE_A, VALUE_B)).toBe(false); + expect(lessThan(VALUE_B, VALUE_A)).toBe(true); + expect(lessThan(VALUE_A, VALUE_A)).toBe(false); + expect(lessThan(NEGATIVE_VALUE, VALUE_A)).toBe(true); + }); + + test('lessThanOrEqualTo', () => { + expect(() => lessThanOrEqualTo(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => lessThanOrEqualTo(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(lessThanOrEqualTo(VALUE_A, VALUE_B)).toBe(false); + expect(lessThanOrEqualTo(VALUE_B, VALUE_A)).toBe(true); + expect(lessThanOrEqualTo(VALUE_A, VALUE_A)).toBe(true); + expect(lessThanOrEqualTo(NEGATIVE_VALUE, VALUE_A)).toBe(true); + }); }); describe('BigNumber', () => { @@ -92,7 +140,35 @@ describe('BigNumber', () => { test('mod', () => { expect(new BigNumber(VALUE_A).mod(VALUE_B).toString()).toBe(RESULTS.mod); }); + test('pow', () => { expect(new BigNumber(VALUE_A).pow(VALUE_C).toString()).toBe(RESULTS.pow); }); + + test('equal', () => { + expect(new BigNumber(VALUE_A).eq(VALUE_B)).toBe(false); + expect(new BigNumber(VALUE_A).eq(VALUE_A)).toBe(true); + }); + + test('greaterThan', () => { + expect(new BigNumber(VALUE_A).gt(VALUE_B)).toBe(true); + expect(new BigNumber(VALUE_B).gt(VALUE_A)).toBe(false); + }); + + test('greaterThanOrEqualTo', () => { + expect(new BigNumber(VALUE_A).gte(VALUE_B)).toBe(true); + expect(new BigNumber(VALUE_B).gte(VALUE_A)).toBe(false); + expect(new BigNumber(VALUE_A).gte(VALUE_A)).toBe(true); + }); + + test('lessThan', () => { + expect(new BigNumber(VALUE_A).lt(VALUE_B)).toBe(false); + expect(new BigNumber(VALUE_B).lt(VALUE_A)).toBe(true); + }); + + test('lessThanOrEqualTo', () => { + expect(new BigNumber(VALUE_A).lte(VALUE_B)).toBe(false); + expect(new BigNumber(VALUE_B).lte(VALUE_A)).toBe(true); + expect(new BigNumber(VALUE_A).lte(VALUE_A)).toBe(true); + }); }); From f1640c9efe6e71902d8b0fbd5115ff35e8976473 Mon Sep 17 00:00:00 2001 From: Christian Baroni <7061887+christianbaroni@users.noreply.github.com> Date: Mon, 27 May 2024 19:23:38 +0000 Subject: [PATCH 2/2] Add Worklet suffix to safe math functions --- src/__swaps__/safe-math/SafeMath.ts | 170 +++++++------- .../safe-math/__tests__/SafeMath.test.ts | 210 +++++++++--------- 2 files changed, 196 insertions(+), 184 deletions(-) diff --git a/src/__swaps__/safe-math/SafeMath.ts b/src/__swaps__/safe-math/SafeMath.ts index e6f68d487d2..c98ea7536fa 100644 --- a/src/__swaps__/safe-math/SafeMath.ts +++ b/src/__swaps__/safe-math/SafeMath.ts @@ -1,5 +1,5 @@ // Utility function to remove the decimal point and keep track of the number of decimal places -const removeDecimal = (num: string): [bigint, number] => { +const removeDecimalWorklet = (num: string): [bigint, number] => { 'worklet'; const parts = num.split('.'); const decimalPlaces = parts.length === 2 ? parts[1].length : 0; @@ -7,12 +7,12 @@ const removeDecimal = (num: string): [bigint, number] => { return [bigIntNum, decimalPlaces]; }; -const isNumberString = (value: string): boolean => { +const isNumberStringWorklet = (value: string): boolean => { 'worklet'; return /^-?\d+(\.\d+)?$/.test(value); }; -const isZero = (value: string): boolean => { +const isZeroWorklet = (value: string): boolean => { 'worklet'; if (parseFloat(value) === 0) { return true; @@ -21,14 +21,14 @@ const isZero = (value: string): boolean => { }; // Utility function to scale the number up to 20 decimal places -const scaleUp = (bigIntNum: bigint, decimalPlaces: number): bigint => { +const scaleUpWorklet = (bigIntNum: bigint, decimalPlaces: number): bigint => { 'worklet'; const scaleFactor = BigInt(10) ** BigInt(20); return (bigIntNum * scaleFactor) / BigInt(10) ** BigInt(decimalPlaces); }; // Utility function to format the result with 20 decimal places and remove trailing zeros -const formatResult = (result: bigint): string => { +const formatResultWorklet = (result: bigint): string => { 'worklet'; const isNegative = result < 0; const absResult = isNegative ? -result : result; @@ -41,181 +41,181 @@ const formatResult = (result: bigint): string => { }; // Sum function -export function sum(num1: string, num2: string): string { +export function sumWorklet(num1: string, num2: string): string { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(num1)) { + if (isZeroWorklet(num1)) { return num2; } - if (isZero(num2)) { + if (isZeroWorklet(num2)) { return num1; } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); const result = scaledBigInt1 + scaledBigInt2; - return formatResult(result); + return formatResultWorklet(result); } // Subtract function -export function sub(num1: string, num2: string): string { +export function subWorklet(num1: string, num2: string): string { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(num2)) { + if (isZeroWorklet(num2)) { return num1; } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); const result = scaledBigInt1 - scaledBigInt2; - return formatResult(result); + return formatResultWorklet(result); } // Multiply function -export function mul(num1: string, num2: string): string { +export function mulWorklet(num1: string, num2: string): string { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(num1) || isZero(num2)) { + if (isZeroWorklet(num1) || isZeroWorklet(num2)) { return '0'; } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); const result = (scaledBigInt1 * scaledBigInt2) / BigInt(10) ** BigInt(20); - return formatResult(result); + return formatResultWorklet(result); } // Divide function -export function div(num1: string, num2: string): string { +export function divWorklet(num1: string, num2: string): string { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(num2)) { + if (isZeroWorklet(num2)) { throw new Error('Division by zero'); } - if (isZero(num1)) { + if (isZeroWorklet(num1)) { return '0'; } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); const result = (scaledBigInt1 * BigInt(10) ** BigInt(20)) / scaledBigInt2; - return formatResult(result); + return formatResultWorklet(result); } // Modulus function -export function mod(num1: string, num2: string): string { +export function modWorklet(num1: string, num2: string): string { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(num2)) { + if (isZeroWorklet(num2)) { throw new Error('Division by zero'); } - if (isZero(num1)) { + if (isZeroWorklet(num1)) { return '0'; } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); const result = scaledBigInt1 % scaledBigInt2; - return formatResult(result); + return formatResultWorklet(result); } // Power function -export function pow(base: string, exponent: string): string { +export function powWorklet(base: string, exponent: string): string { 'worklet'; - if (!isNumberString(base) || !isNumberString(exponent)) { + if (!isNumberStringWorklet(base) || !isNumberStringWorklet(exponent)) { throw new Error('Arguments must be a numeric string'); } - if (isZero(base)) { + if (isZeroWorklet(base)) { return '0'; } - if (isZero(exponent)) { + if (isZeroWorklet(exponent)) { return '1'; } - const [bigIntBase, decimalPlaces] = removeDecimal(base); - const scaledBigIntBase = scaleUp(bigIntBase, decimalPlaces); + const [bigIntBase, decimalPlaces] = removeDecimalWorklet(base); + const scaledBigIntBase = scaleUpWorklet(bigIntBase, decimalPlaces); const result = scaledBigIntBase ** BigInt(exponent) / BigInt(10) ** BigInt(20); - return formatResult(result); + return formatResultWorklet(result); } // Equality function -export function equal(num1: string, num2: string): boolean { +export function equalWorklet(num1: string, num2: string): boolean { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); return scaledBigInt1 === scaledBigInt2; } // Greater than function -export function greaterThan(num1: string, num2: string): boolean { +export function greaterThanWorklet(num1: string, num2: string): boolean { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); return scaledBigInt1 > scaledBigInt2; } // Greater than or equal to function -export function greaterThanOrEqualTo(num1: string, num2: string): boolean { +export function greaterThanOrEqualToWorklet(num1: string, num2: string): boolean { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); return scaledBigInt1 >= scaledBigInt2; } // Less than function -export function lessThan(num1: string, num2: string): boolean { +export function lessThanWorklet(num1: string, num2: string): boolean { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); return scaledBigInt1 < scaledBigInt2; } // Less than or equal to function -export function lessThanOrEqualTo(num1: string, num2: string): boolean { +export function lessThanOrEqualToWorklet(num1: string, num2: string): boolean { 'worklet'; - if (!isNumberString(num1) || !isNumberString(num2)) { + if (!isNumberStringWorklet(num1) || !isNumberStringWorklet(num2)) { throw new Error('Arguments must be a numeric string'); } - const [bigInt1, decimalPlaces1] = removeDecimal(num1); - const [bigInt2, decimalPlaces2] = removeDecimal(num2); - const scaledBigInt1 = scaleUp(bigInt1, decimalPlaces1); - const scaledBigInt2 = scaleUp(bigInt2, decimalPlaces2); + const [bigInt1, decimalPlaces1] = removeDecimalWorklet(num1); + const [bigInt2, decimalPlaces2] = removeDecimalWorklet(num2); + const scaledBigInt1 = scaleUpWorklet(bigInt1, decimalPlaces1); + const scaledBigInt2 = scaleUpWorklet(bigInt2, decimalPlaces2); return scaledBigInt1 <= scaledBigInt2; } diff --git a/src/__swaps__/safe-math/__tests__/SafeMath.test.ts b/src/__swaps__/safe-math/__tests__/SafeMath.test.ts index 94e487c5cf4..a80196afeec 100644 --- a/src/__swaps__/safe-math/__tests__/SafeMath.test.ts +++ b/src/__swaps__/safe-math/__tests__/SafeMath.test.ts @@ -1,5 +1,17 @@ -import { sum, sub, mul, div, mod, pow, equal, greaterThan, greaterThanOrEqualTo, lessThan, lessThanOrEqualTo } from '../SafeMath'; import BigNumber from 'bignumber.js'; +import { + divWorklet, + equalWorklet, + greaterThanOrEqualToWorklet, + greaterThanWorklet, + lessThanOrEqualToWorklet, + lessThanWorklet, + modWorklet, + mulWorklet, + powWorklet, + subWorklet, + sumWorklet, +} from '../SafeMath'; const RESULTS = { sum: '1247244.585', @@ -19,104 +31,104 @@ const ONE = '1'; const NON_NUMERIC_STRING = 'abc'; describe('SafeMath', () => { - test('sum', () => { - expect(() => sum(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => sum(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(sum(ZERO, ZERO)).toBe(ZERO); - expect(sum(VALUE_A, ZERO)).toBe(VALUE_A); - expect(sum(ZERO, VALUE_B)).toBe(VALUE_B); - expect(sum(VALUE_A, VALUE_B)).toBe(RESULTS.sum); - }); - - test('sub', () => { - expect(() => sub(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => sub(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(sub(ZERO, ZERO)).toBe(ZERO); - expect(sub(VALUE_A, ZERO)).toBe(VALUE_A); - expect(sub(ZERO, VALUE_B)).toBe(`-${VALUE_B}`); - expect(sub(NEGATIVE_VALUE, ZERO)).toBe(NEGATIVE_VALUE); - expect(sub(VALUE_A, VALUE_B)).toBe(RESULTS.sub); - }); - - test('mul', () => { - expect(() => mul(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => mul(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(mul(ZERO, ZERO)).toBe(ZERO); - expect(mul(VALUE_A, ZERO)).toBe(ZERO); - expect(mul(ZERO, VALUE_B)).toBe(ZERO); - expect(mul(VALUE_A, VALUE_B)).toBe(RESULTS.mul); - }); - - test('div', () => { - expect(() => div(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => div(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(() => div(ZERO, ZERO)).toThrow('Division by zero'); - expect(() => div(VALUE_A, ZERO)).toThrow('Division by zero'); - expect(div(ZERO, VALUE_B)).toBe(ZERO); - expect(div(VALUE_A, VALUE_B)).toBe(RESULTS.div); - }); - - test('mod', () => { - expect(() => mod(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => mod(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(() => mod(ZERO, ZERO)).toThrow('Division by zero'); - expect(() => mod(VALUE_A, ZERO)).toThrow('Division by zero'); - expect(mod(ZERO, VALUE_B)).toBe(ZERO); - expect(mod(VALUE_A, VALUE_B)).toBe(RESULTS.mod); - }); - - test('pow', () => { - expect(() => pow(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => pow(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(pow(ZERO, VALUE_B)).toBe(ZERO); - expect(pow(VALUE_A, ZERO)).toBe(ONE); - expect(pow(ZERO, VALUE_B)).toBe(ZERO); - expect(pow(VALUE_A, VALUE_C)).toBe(RESULTS.pow); - }); - - test('equal', () => { - expect(() => equal(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => equal(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(equal(ZERO, ZERO)).toBe(true); - expect(equal(VALUE_A, VALUE_A)).toBe(true); - expect(equal(VALUE_A, VALUE_B)).toBe(false); - expect(equal(NEGATIVE_VALUE, NEGATIVE_VALUE)).toBe(true); - }); - - test('greaterThan', () => { - expect(() => greaterThan(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => greaterThan(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(greaterThan(VALUE_A, VALUE_B)).toBe(true); - expect(greaterThan(VALUE_B, VALUE_A)).toBe(false); - expect(greaterThan(VALUE_A, VALUE_A)).toBe(false); - expect(greaterThan(NEGATIVE_VALUE, VALUE_A)).toBe(false); - }); - - test('greaterThanOrEqualTo', () => { - expect(() => greaterThanOrEqualTo(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => greaterThanOrEqualTo(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(greaterThanOrEqualTo(VALUE_A, VALUE_B)).toBe(true); - expect(greaterThanOrEqualTo(VALUE_B, VALUE_A)).toBe(false); - expect(greaterThanOrEqualTo(VALUE_A, VALUE_A)).toBe(true); - expect(greaterThanOrEqualTo(NEGATIVE_VALUE, VALUE_A)).toBe(false); - }); - - test('lessThan', () => { - expect(() => lessThan(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => lessThan(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(lessThan(VALUE_A, VALUE_B)).toBe(false); - expect(lessThan(VALUE_B, VALUE_A)).toBe(true); - expect(lessThan(VALUE_A, VALUE_A)).toBe(false); - expect(lessThan(NEGATIVE_VALUE, VALUE_A)).toBe(true); - }); - - test('lessThanOrEqualTo', () => { - expect(() => lessThanOrEqualTo(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); - expect(() => lessThanOrEqualTo(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); - expect(lessThanOrEqualTo(VALUE_A, VALUE_B)).toBe(false); - expect(lessThanOrEqualTo(VALUE_B, VALUE_A)).toBe(true); - expect(lessThanOrEqualTo(VALUE_A, VALUE_A)).toBe(true); - expect(lessThanOrEqualTo(NEGATIVE_VALUE, VALUE_A)).toBe(true); + test('sumWorklet', () => { + expect(() => sumWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => sumWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(sumWorklet(ZERO, ZERO)).toBe(ZERO); + expect(sumWorklet(VALUE_A, ZERO)).toBe(VALUE_A); + expect(sumWorklet(ZERO, VALUE_B)).toBe(VALUE_B); + expect(sumWorklet(VALUE_A, VALUE_B)).toBe(RESULTS.sum); + }); + + test('subWorklet', () => { + expect(() => subWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => subWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(subWorklet(ZERO, ZERO)).toBe(ZERO); + expect(subWorklet(VALUE_A, ZERO)).toBe(VALUE_A); + expect(subWorklet(ZERO, VALUE_B)).toBe(`-${VALUE_B}`); + expect(subWorklet(NEGATIVE_VALUE, ZERO)).toBe(NEGATIVE_VALUE); + expect(subWorklet(VALUE_A, VALUE_B)).toBe(RESULTS.sub); + }); + + test('mulWorklet', () => { + expect(() => mulWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => mulWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(mulWorklet(ZERO, ZERO)).toBe(ZERO); + expect(mulWorklet(VALUE_A, ZERO)).toBe(ZERO); + expect(mulWorklet(ZERO, VALUE_B)).toBe(ZERO); + expect(mulWorklet(VALUE_A, VALUE_B)).toBe(RESULTS.mul); + }); + + test('divWorklet', () => { + expect(() => divWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => divWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(() => divWorklet(ZERO, ZERO)).toThrow('Division by zero'); + expect(() => divWorklet(VALUE_A, ZERO)).toThrow('Division by zero'); + expect(divWorklet(ZERO, VALUE_B)).toBe(ZERO); + expect(divWorklet(VALUE_A, VALUE_B)).toBe(RESULTS.div); + }); + + test('modWorklet', () => { + expect(() => modWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => modWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(() => modWorklet(ZERO, ZERO)).toThrow('Division by zero'); + expect(() => modWorklet(VALUE_A, ZERO)).toThrow('Division by zero'); + expect(modWorklet(ZERO, VALUE_B)).toBe(ZERO); + expect(modWorklet(VALUE_A, VALUE_B)).toBe(RESULTS.mod); + }); + + test('powWorklet', () => { + expect(() => powWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => powWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(powWorklet(ZERO, VALUE_B)).toBe(ZERO); + expect(powWorklet(VALUE_A, ZERO)).toBe(ONE); + expect(powWorklet(ZERO, VALUE_B)).toBe(ZERO); + expect(powWorklet(VALUE_A, VALUE_C)).toBe(RESULTS.pow); + }); + + test('equalWorklet', () => { + expect(() => equalWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => equalWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(equalWorklet(ZERO, ZERO)).toBe(true); + expect(equalWorklet(VALUE_A, VALUE_A)).toBe(true); + expect(equalWorklet(VALUE_A, VALUE_B)).toBe(false); + expect(equalWorklet(NEGATIVE_VALUE, NEGATIVE_VALUE)).toBe(true); + }); + + test('greaterThanWorklet', () => { + expect(() => greaterThanWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => greaterThanWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(greaterThanWorklet(VALUE_A, VALUE_B)).toBe(true); + expect(greaterThanWorklet(VALUE_B, VALUE_A)).toBe(false); + expect(greaterThanWorklet(VALUE_A, VALUE_A)).toBe(false); + expect(greaterThanWorklet(NEGATIVE_VALUE, VALUE_A)).toBe(false); + }); + + test('greaterThanOrEqualToWorklet', () => { + expect(() => greaterThanOrEqualToWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => greaterThanOrEqualToWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(greaterThanOrEqualToWorklet(VALUE_A, VALUE_B)).toBe(true); + expect(greaterThanOrEqualToWorklet(VALUE_B, VALUE_A)).toBe(false); + expect(greaterThanOrEqualToWorklet(VALUE_A, VALUE_A)).toBe(true); + expect(greaterThanOrEqualToWorklet(NEGATIVE_VALUE, VALUE_A)).toBe(false); + }); + + test('lessThanWorklet', () => { + expect(() => lessThanWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => lessThanWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(lessThanWorklet(VALUE_A, VALUE_B)).toBe(false); + expect(lessThanWorklet(VALUE_B, VALUE_A)).toBe(true); + expect(lessThanWorklet(VALUE_A, VALUE_A)).toBe(false); + expect(lessThanWorklet(NEGATIVE_VALUE, VALUE_A)).toBe(true); + }); + + test('lessThanOrEqualToWorklet', () => { + expect(() => lessThanOrEqualToWorklet(NON_NUMERIC_STRING, VALUE_B)).toThrow('Arguments must be a numeric string'); + expect(() => lessThanOrEqualToWorklet(VALUE_A, NON_NUMERIC_STRING)).toThrow('Arguments must be a numeric string'); + expect(lessThanOrEqualToWorklet(VALUE_A, VALUE_B)).toBe(false); + expect(lessThanOrEqualToWorklet(VALUE_B, VALUE_A)).toBe(true); + expect(lessThanOrEqualToWorklet(VALUE_A, VALUE_A)).toBe(true); + expect(lessThanOrEqualToWorklet(NEGATIVE_VALUE, VALUE_A)).toBe(true); }); });