1- /**
2- * https://github.com/rollup/plugins/blob/master/packages/json/src/index.js
3- *
4- * This source code is licensed under the MIT license found in the
5- * LICENSE file at
6- * https://github.com/rollup/plugins/blob/master/LICENSE
7- */
8-
9- import { dataToEsm , makeLegalIdentifier } from '@rollup/pluginutils'
10- import { viteJsonPlugin as nativeJsonPlugin } from 'rolldown/experimental'
11- import { SPECIAL_QUERY_RE } from '../constants'
12- import type { Plugin } from '../plugin'
13- import { stripBomTag } from '../utils'
14- import { inlineRE , noInlineRE } from './asset'
15-
161export interface JsonOptions {
172 /**
183 * Generate a named export for every property of the JSON object
@@ -28,135 +13,7 @@ export interface JsonOptions {
2813 stringify ?: boolean | 'auto'
2914}
3015
31- // Custom json filter for vite
32- const jsonExtRE = / \. j s o n (?: $ | \? ) (? ! c o m m o n j s - (?: p r o x y | e x t e r n a l ) ) /
33-
34- const jsonObjRE = / ^ \s * \{ /
35-
3616const jsonLangs = `\\.(?:json|json5)(?:$|\\?)`
3717const jsonLangRE = new RegExp ( jsonLangs )
3818export const isJSONRequest = ( request : string ) : boolean =>
3919 jsonLangRE . test ( request )
40-
41- export function jsonPlugin (
42- options : Required < JsonOptions > ,
43- isBuild : boolean ,
44- enableNativePlugin : boolean ,
45- ) : Plugin {
46- if ( enableNativePlugin ) {
47- return nativeJsonPlugin ( { ...options , minify : isBuild } )
48- }
49-
50- return {
51- name : 'vite:json' ,
52-
53- transform : {
54- filter : {
55- id : { include : jsonExtRE , exclude : SPECIAL_QUERY_RE } ,
56- // don't transform if the file is already transformed to a different format
57- moduleType : [ 'json' ] ,
58- } ,
59- handler ( json , id ) {
60- if ( inlineRE . test ( id ) || noInlineRE . test ( id ) ) {
61- this . warn (
62- `\n` +
63- `Using ?inline or ?no-inline for JSON imports will have no effect.\n` +
64- `Please use ?url&inline or ?url&no-inline to control JSON file inlining behavior.\n` ,
65- )
66- }
67-
68- json = stripBomTag ( json )
69-
70- try {
71- if ( options . stringify !== false ) {
72- if ( options . namedExports && jsonObjRE . test ( json ) ) {
73- const parsed = JSON . parse ( json )
74- const keys = Object . keys ( parsed )
75-
76- let code = ''
77- let defaultObjectCode = '{\n'
78- for ( const key of keys ) {
79- if ( key === makeLegalIdentifier ( key ) ) {
80- code += `export const ${ key } = ${ serializeValue ( parsed [ key ] ) } ;\n`
81- defaultObjectCode += ` ${ key } ,\n`
82- } else {
83- defaultObjectCode += ` ${ JSON . stringify ( key ) } : ${ serializeValue ( parsed [ key ] ) } ,\n`
84- }
85- }
86- defaultObjectCode += '}'
87-
88- code += `export default ${ defaultObjectCode } ;\n`
89- return {
90- code,
91- map : { mappings : '' } ,
92- moduleType : 'js' ,
93- }
94- }
95-
96- if (
97- options . stringify === true ||
98- // use 10kB as a threshold for 'auto'
99- // https://v8.dev/blog/cost-of-javascript-2019#:~:text=A%20good%20rule%20of%20thumb%20is%20to%20apply%20this%20technique%20for%20objects%20of%2010%20kB%20or%20larger
100- json . length > 10 * 1000
101- ) {
102- // during build, parse then double-stringify to remove all
103- // unnecessary whitespaces to reduce bundle size.
104- if ( isBuild ) {
105- json = JSON . stringify ( JSON . parse ( json ) )
106- }
107-
108- return {
109- code : `export default /* #__PURE__ */ JSON.parse(${ JSON . stringify ( json ) } )` ,
110- map : { mappings : '' } ,
111- moduleType : 'js' ,
112- }
113- }
114- }
115-
116- return {
117- code : dataToEsm ( JSON . parse ( json ) , {
118- preferConst : true ,
119- namedExports : options . namedExports ,
120- } ) ,
121- map : { mappings : '' } ,
122- moduleType : 'js' ,
123- }
124- } catch ( e ) {
125- const position = extractJsonErrorPosition ( e . message , json . length )
126- const msg = position
127- ? `, invalid JSON syntax found at position ${ position } `
128- : `.`
129- this . error ( `Failed to parse JSON file` + msg , position )
130- }
131- } ,
132- } ,
133- }
134- }
135-
136- function serializeValue ( value : unknown ) : string {
137- const valueAsString = JSON . stringify ( value )
138- // use 10kB as a threshold
139- // https://v8.dev/blog/cost-of-javascript-2019#:~:text=A%20good%20rule%20of%20thumb%20is%20to%20apply%20this%20technique%20for%20objects%20of%2010%20kB%20or%20larger
140- if (
141- typeof value === 'object' &&
142- value != null &&
143- valueAsString . length > 10 * 1000
144- ) {
145- return `/* #__PURE__ */ JSON.parse(${ JSON . stringify ( valueAsString ) } )`
146- }
147- return valueAsString
148- }
149-
150- export function extractJsonErrorPosition (
151- errorMessage : string ,
152- inputLength : number ,
153- ) : number | undefined {
154- if ( errorMessage . startsWith ( 'Unexpected end of JSON input' ) ) {
155- return inputLength - 1
156- }
157-
158- const errorMessageList = / a t p o s i t i o n ( \d + ) / . exec ( errorMessage )
159- return errorMessageList
160- ? Math . max ( parseInt ( errorMessageList [ 1 ] , 10 ) - 1 , 0 )
161- : undefined
162- }
0 commit comments