@parsekit/string-to-number
v1.0.0
Published
A zero-dependency TypeScript utility for safely converting strings and primitive values to finite numbers
Downloads
170
Maintainers
Readme
@parsekit/string-to-number
A zero-dependency TypeScript utility for safely converting numeric strings and primitive number values into finite JavaScript numbers.
Unlike JavaScript coercion with unary +, ParseKit validates the complete
input, rejects ambiguous values, prevents NaN and infinity from being
returned as successful results, and provides strict-mode errors when required.
Features
- Zero runtime dependencies
- Strong TypeScript types and generated declarations
- Full-string decimal validation
- Integer, decimal, and scientific notation support
- Optional validated numeric separators such as
"1_000" - Safe-integer protection by default
- Configurable whitespace handling
- Non-strict parsing that returns
undefinedfor invalid input - Strict parsing with
StringToNumberError - No logging, mutation, I/O, or environment access
Installation
npm install @parsekit/string-to-numberpnpm add @parsekit/string-to-number
yarn add @parsekit/string-to-numberBasic usage
import { stringToNumber } from '@parsekit/string-to-number';
stringToNumber('42'); // 42
stringToNumber('-3.14'); // -3.14
stringToNumber('1e3'); // 1000
stringToNumber(42); // 42
stringToNumber('invalid'); // undefinedBecause invalid input returns undefined, callers can handle it explicitly:
const parsedPort = stringToNumber(process.env.PORT);
if (parsedPort === undefined) {
throw new Error('PORT must be a valid number');
}Strict parsing
Use stringToNumberStrict when invalid input should stop execution or be
handled as an exception:
import {
stringToNumberStrict,
StringToNumberError
} from '@parsekit/string-to-number';
try {
const port = stringToNumberStrict(process.env.PORT);
console.log(port);
} catch (error) {
if (error instanceof StringToNumberError) {
console.error(error.message);
}
}stringToNumberStrict returns number when successful and throws
StringToNumberError when the input cannot be safely converted.
Options
interface StringToNumberOptions {
strict?: boolean;
trimInput?: boolean;
allowNumericSeparators?: boolean;
allowUnsafeIntegers?: boolean;
}strict
Defaults to false.
false: invalid input returnsundefined.true: invalid input throwsStringToNumberError.
stringToNumber('not-a-number', { strict: true });
// throws StringToNumberErrortrimInput
Defaults to true.
stringToNumber(' 42 '); // 42
stringToNumber(' 42 ', { trimInput: false });
// undefinedallowNumericSeparators
Defaults to false.
Numeric separators are accepted only when explicitly enabled and correctly placed between digits:
stringToNumber('1_000', { allowNumericSeparators: true });
// 1000
stringToNumber('-1_000.50', { allowNumericSeparators: true });
// -1000.5
stringToNumber('-1_000e-3', { allowNumericSeparators: true });
// -1Malformed separators remain invalid:
stringToNumber('1__000', { allowNumericSeparators: true }); // undefined
stringToNumber('1_000_', { allowNumericSeparators: true }); // undefined
stringToNumber('_1000', { allowNumericSeparators: true }); // undefinedJavaScript source literals such as 1_000 are already passed to the function
as the number 1000:
const value = 1_000;
stringToNumber(value); // 1000allowUnsafeIntegers
Defaults to false.
JavaScript numbers cannot represent every integer outside the safe-integer range exactly. Unsafe integer inputs are rejected by default:
stringToNumber('9007199254740993'); // undefinedOpt in only when ordinary JavaScript number precision is acceptable:
stringToNumber('9007199254740993', {
allowUnsafeIntegers: true
});
// 9007199254740992Use a future BigInt-oriented parser when exact arbitrary-size integers are required.
Accepted values
| Input | Result |
| --- | ---: |
| 42 | 42 |
| -42 | -42 |
| "42" | 42 |
| "-3.14" | -3.14 |
| ".5" | 0.5 |
| "1." | 1 |
| "1e3" | 1000 |
| "-2.5E-2" | -0.025 |
| " 42 " | 42 by default |
| -0 | negative zero is preserved |
Rejected values
The following return undefined in normal mode and throw in strict mode:
stringToNumber('');
stringToNumber(' ');
stringToNumber(null);
stringToNumber(undefined);
stringToNumber('42px');
stringToNumber('1.2.3');
stringToNumber('0x10');
stringToNumber('0b10');
stringToNumber('0o10');
stringToNumber('NaN');
stringToNumber('Infinity');
stringToNumber(NaN);
stringToNumber(Infinity);BigInt values, symbols, objects, arrays, functions, and boxed primitives are also rejected safely at runtime. TypeScript callers receive compile-time protection, while JavaScript callers receive the same runtime behavior.
Exported API
type StringNumber = string | number | null | undefined;
interface StringToNumberOptions {
strict?: boolean;
trimInput?: boolean;
allowNumericSeparators?: boolean;
allowUnsafeIntegers?: boolean;
}
class StringToNumberError extends Error {
readonly value: unknown;
}
function stringToNumber(
value: StringNumber,
options?: StringToNumberOptions
): number | undefined;
function stringToNumberStrict(
value: StringNumber,
options?: Omit<StringToNumberOptions, 'strict'>
): number;
function stringToNumberWithOptions(
value: StringNumber,
options: StringToNumberOptions
): number | undefined;The default export is stringToNumber.
Framework and runtime compatibility
The parser is a pure function and does not depend on a framework. It can be used from TypeScript and JavaScript projects built with Node.js, React, Vue, Angular, Svelte, Next.js, Vite, Webpack, Rollup, or esbuild.
The package currently publishes a CommonJS build with TypeScript declarations. Bundlers and TypeScript projects can use standard named or default imports.
Development
npm install
npm test
npm run lint
npm run build
npm pack --dry-runThe test suite is required to maintain 100% statement, branch, function, and line coverage.
Related packages
ParseKit provides focused parsing utilities with consistent naming, TypeScript-first APIs, explicit failure behavior, and zero runtime dependencies.
@parsekit/string-to-boolean@parsekit/string-to-number
License
MIT © Srikar Phani Kumar Marti
