UNPKG

@0xtorch/big-decimal

Version:

An arbitrary precision Decimal type for TypeScript that extends BigInt.

73 lines 2.76 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.createBigDecimal = void 0; const createBigDecimal = (value, decimals) => { if (typeof value === 'string') { return createBigDecimalFromString(value, decimals); } if (typeof value === 'number') { return createBigDecimalFromString(value.toString(), decimals); } return createBigDecimalFromBigint(value, decimals); }; exports.createBigDecimal = createBigDecimal; const createBigDecimalFromString = (value, decimals) => { const splitedValue = value.replaceAll(' ', '').split(/[eE]/); const baseValue = splitedValue[0]; const exponent = splitedValue[1]; const isNegative = baseValue.startsWith('-'); const absText = isNegative ? baseValue.slice(1) : baseValue; const numberText = absText .replaceAll('+', '') .replaceAll(',', '') .replaceAll('_', ''); const [intText, decimalText] = numberText.split('.'); const numberRegExp = /^\d+$/; if (!numberRegExp.test(intText) || (decimalText !== undefined && decimalText.length > 0 && !numberRegExp.test(decimalText))) { throw new Error(`Invalid decimal format value: ${baseValue}`); } const formattedDecimalText = decimalText !== undefined && decimalText.length > 0 ? decimalText.replace(/0+$/, '') : ''; const formattedDecimals = formattedDecimalText.length; const adjustedDecimalText = adjustDecimalText(decimals, formattedDecimalText, formattedDecimals); const valueBn = BigInt(`${isNegative ? '-' : ''}${intText}${adjustedDecimalText}`); const baseDecimals = decimals === undefined ? formattedDecimals : decimals; if (exponent === undefined) { return { value: valueBn, decimals: baseDecimals, }; } const exponentNumber = Number(exponent); const decimalsWithExponent = baseDecimals - exponentNumber; return decimalsWithExponent < 0 ? { value: valueBn * 10n ** BigInt(-decimalsWithExponent), decimals: 0, } : { value: valueBn, decimals: decimalsWithExponent, }; }; const adjustDecimalText = (decimals, formattedDecimalText, formattedDecimals) => { if (decimals === undefined) { return formattedDecimalText; } if (decimals > formattedDecimals) { return formattedDecimalText.padEnd(decimals, '0'); } if (decimals < formattedDecimals) { return formattedDecimalText.slice(0, decimals); } return formattedDecimalText; }; const createBigDecimalFromBigint = (value, decimals) => ({ value, decimals: decimals ?? 0, }); //# sourceMappingURL=createBigDecimal.js.map