@@ -298,6 +298,14 @@ function compareVersions(version1, version2, operator) {
298298 }
299299}
300300
301+ // Module-level constants for parseJSONWithBigInt
302+ const CONTEXT_SUPPORTED_VERSION = '21.0.0.0' ;
303+ const isContextSupported = compareVersions (
304+ process . version . substring ( 1 ) ,
305+ CONTEXT_SUPPORTED_VERSION ,
306+ '>='
307+ ) ;
308+
301309/**
302310 * Parse JSON string with support for large integers (beyond Number.MAX_SAFE_INTEGER).
303311 * Large integers are automatically converted to strings to preserve precision.
@@ -318,16 +326,7 @@ function compareVersions(version1, version2, operator) {
318326 * // Returns: { value: 100 }
319327 */
320328function parseJSONWithBigInt ( str ) {
321- const contextSupportedVersion = '21.0.0.0' ;
322- const currentVersion = process . version ;
323- const isContextSupported = compareVersions (
324- currentVersion . substring ( 1 , currentVersion . length ) ,
325- contextSupportedVersion ,
326- '>='
327- ) ;
328-
329- // For nodejs >= 21.0.0, we leverage context parameter to
330- // convert unsafe integer to string.
329+ // For Node.js >= 21.0.0, use native context parameter
331330 // See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/JSON/parse
332331 if ( isContextSupported ) {
333332 return JSON . parse ( str , ( key , value , context ) => {
@@ -344,13 +343,18 @@ function parseJSONWithBigInt(str) {
344343 // For older Node.js versions, preprocess the JSON string to convert
345344 // large integers (outside the safe integer range) to strings before parsing.
346345 // This replaces the functionality of json-bigint package.
346+ // The regex matches integers that are actual JSON values, not inside strings.
347+ // It matches after: colon (:), comma (,), or open bracket ([)
348+ // and before: comma (,), close brace ( }), or close bracket (])
347349 const processed = str . replace (
348- / : \s * ( - ? \d + ) (? = \s * [ , } \] ] ) / g,
350+ / (?: [: , [ ] ) \s * ( - ? \d + ) (? = \s * [ , } \] ] ) / g,
349351 ( match , number ) => {
350352 const num = Number ( number ) ;
351- // If the number is not safe, keep it as a string
353+ // If the number is not safe, convert it to a string
352354 if ( ! Number . isSafeInteger ( num ) ) {
353- return `: "${ number } "` ;
355+ // Preserve the prefix character (: or , or [)
356+ const prefix = match . charAt ( 0 ) ;
357+ return `${ prefix } "${ number } "` ;
354358 }
355359 return match ;
356360 }
0 commit comments