@prantlf/jsonlint 14.0.3 → 15.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/README.md +19 -2
- package/lib/cli.js +75 -14
- package/lib/formatter.js +3 -3
- package/lib/jsonlint.js +85 -77
- package/lib/printer.js +16 -8
- package/lib/sorter.js +22 -5
- package/lib/validator.js +4 -2
- package/package.json +20 -36
- package/web/ajv.min.js +5 -5
- package/web/ajv.min.js.map +1 -1
- package/web/formatter.min.js +4 -4
- package/web/formatter.min.js.map +2 -2
- package/web/jsonlint.html +38 -3
- package/web/jsonlint.min.js +9 -9
- package/web/jsonlint.min.js.map +3 -3
- package/web/printer.min.js +3 -3
- package/web/printer.min.js.map +2 -2
- package/web/sorter.min.js +1 -1
- package/web/sorter.min.js.map +3 -3
- package/web/validator.min.js +3 -3
- package/web/validator.min.js.map +2 -2
package/LICENSE
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
MIT License
|
|
2
2
|
|
|
3
3
|
Copyright (c) 2012-2018 Zachary Carter
|
|
4
|
-
Copyright (c) 2019-
|
|
4
|
+
Copyright (c) 2019-2024 Ferdinand Prantl
|
|
5
5
|
|
|
6
6
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
7
7
|
of this software and associated documentation files (the "Software"), to deal
|
package/README.md
CHANGED
|
@@ -21,7 +21,7 @@ This is a fork of the original project ([zaach/jsonlint](https://github.com/zaac
|
|
|
21
21
|
* Offers pretty-printing including comment-stripping and object keys without quotes (JSON5).
|
|
22
22
|
* Prefers the native JSON parser if possible to run [10x faster than the custom parser].
|
|
23
23
|
* Reports errors with rich additional information. From the JSON Schema validation too.
|
|
24
|
-
* Consumes configuration from both command line and [configuration files](configuration).
|
|
24
|
+
* Consumes configuration from both command line and [configuration files](#configuration).
|
|
25
25
|
* Implements JavaScript modules using [UMD] to work in Node.js, in a browser, everywhere.
|
|
26
26
|
* Depends on up-to-date npm modules with no installation warnings.
|
|
27
27
|
* Small size - 18.4 kB minified, 6.45 kB gzipped, 5.05 kB brotlied.
|
|
@@ -120,7 +120,15 @@ Usage: `jsonlint [options] [--] [<file, directory, pattern> ...]`
|
|
|
120
120
|
|
|
121
121
|
-f, --config <file> read options from a custom configuration file
|
|
122
122
|
-F, --no-config disable searching for configuration files
|
|
123
|
+
--ignore-proto-key ignore occurrences of "__proto__" object key
|
|
124
|
+
--ignore-prototype-keys ignore all keys from "Object.prototype"
|
|
123
125
|
-s, --sort-keys sort object keys (not when prettifying)
|
|
126
|
+
--sort-keys-ignore-case sort object keys ignoring the letter case
|
|
127
|
+
--sort-keys-locale <id> locale identifier to sort object keys with
|
|
128
|
+
(or "default" for the system default)
|
|
129
|
+
--sort-keys-case-first <id> order if only letter case is different
|
|
130
|
+
("upper", "lower" and "false" are allowed)
|
|
131
|
+
--sort-keys-numeric sort by numbers recognised in object keys
|
|
124
132
|
-E, --extensions <ext...> file extensions to process for directory walk
|
|
125
133
|
(default: json, JSON)
|
|
126
134
|
-i, --in-place overwrite the input files
|
|
@@ -154,6 +162,7 @@ Usage: `jsonlint [options] [--] [<file, directory, pattern> ...]`
|
|
|
154
162
|
--enforce-double-quotes surrounds all strings with double quotes
|
|
155
163
|
--enforce-single-quotes surrounds all strings with single quotes
|
|
156
164
|
--trim-trailing-commas omit trailing commas from objects and arrays
|
|
165
|
+
--succeed-with-no-files succeed (exit code 0) if no files were found
|
|
157
166
|
-v, --version output the version number
|
|
158
167
|
-h, --help display help for command
|
|
159
168
|
|
|
@@ -192,7 +201,13 @@ The configuration is an object with the following properties, described above, w
|
|
|
192
201
|
| Parameter | Alias |
|
|
193
202
|
| --------- | ----- |
|
|
194
203
|
| patterns | |
|
|
204
|
+
| ignore-proto-key | ignoreProtoKey |
|
|
205
|
+
| ignore-prototype-keys | ignorePrototypeKeys |
|
|
195
206
|
| sort-keys | sortKeys |
|
|
207
|
+
| sort-keys-ignore-case | sortKeysIgnoreCase |
|
|
208
|
+
| sort-keys-locale | sortKeysLocale |
|
|
209
|
+
| sort-keys-case-first | sortKeysCaseFirst |
|
|
210
|
+
| sort-keys-numeric | sortKeysNumeric |
|
|
196
211
|
| extensions | |
|
|
197
212
|
| in-place | inPlace |
|
|
198
213
|
| diff | |
|
|
@@ -263,6 +278,8 @@ The `parse` method offers more detailed [error information](#error-handling), th
|
|
|
263
278
|
| `ignoreTrailingCommas` | ignores trailing commas in objects and arrays (boolean) |
|
|
264
279
|
| `allowSingleQuotedStrings` | accepts strings delimited by single-quotes too (boolean) |
|
|
265
280
|
| `allowDuplicateObjectKeys` | allows reporting duplicate object keys as an error (boolean) |
|
|
281
|
+
| `ignoreProtoKey` | ignore occurrences of the `__proto__` object key (boolean) |
|
|
282
|
+
| `ignorePrototypeKeys` | ignore all keys from `Object.prototype` (boolean) |
|
|
266
283
|
| `mode` | sets multiple options according to the type of input data (string) |
|
|
267
284
|
| `reviver` | converts object and array values (function) |
|
|
268
285
|
|
|
@@ -428,7 +445,7 @@ ${reason}`)
|
|
|
428
445
|
|
|
429
446
|
## License
|
|
430
447
|
|
|
431
|
-
Copyright (C) 2012-
|
|
448
|
+
Copyright (C) 2012-2024 Zachary Carter, Ferdinand Prantl
|
|
432
449
|
|
|
433
450
|
Licensed under the [MIT License].
|
|
434
451
|
|
package/lib/cli.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
const { readdirSync, readFileSync, statSync, writeFileSync } = require('fs')
|
|
4
|
-
const { extname, join } = require('path')
|
|
3
|
+
const { readdirSync, readFileSync, statSync, writeFileSync } = require('node:fs')
|
|
4
|
+
const { extname, join } = require('node:path')
|
|
5
5
|
const { isDynamicPattern, sync } = require('fast-glob')
|
|
6
6
|
const { parse, tokenize } = require('./jsonlint')
|
|
7
7
|
const { format } = require('./formatter')
|
|
@@ -17,7 +17,15 @@ Usage: jsonlint [options] [--] [<file, directory, pattern> ...]
|
|
|
17
17
|
Options:
|
|
18
18
|
-f, --config <file> read options from a custom configuration file
|
|
19
19
|
-F, --no-config disable searching for configuration files
|
|
20
|
+
--ignore-proto-key ignore occurrences of "__proto__" object key
|
|
21
|
+
--ignore-prototype-keys ignore all keys from "Object.prototype"
|
|
20
22
|
-s, --sort-keys sort object keys (not when prettifying)
|
|
23
|
+
--sort-keys-ignore-case sort object keys ignoring the letter case
|
|
24
|
+
--sort-keys-locale <id> locale identifier to sort object keys with
|
|
25
|
+
(or "default" for the system default)
|
|
26
|
+
--sort-keys-case-first <id> order if only letter case is different
|
|
27
|
+
("upper", "lower" and "false" are allowed)
|
|
28
|
+
--sort-keys-numeric sort by numbers recognised in object keys
|
|
21
29
|
-E, --extensions <ext...> file extensions to process for directory walk
|
|
22
30
|
(default: json, JSON)
|
|
23
31
|
-i, --in-place overwrite the input files
|
|
@@ -51,6 +59,7 @@ Options:
|
|
|
51
59
|
--enforce-double-quotes surrounds all strings with double quotes
|
|
52
60
|
--enforce-single-quotes surrounds all strings with single quotes
|
|
53
61
|
--trim-trailing-commas omit trailing commas from objects and arrays
|
|
62
|
+
--succeed-with-no-files succeed (exit code 0) if no files were found
|
|
54
63
|
-v, --version output the version number
|
|
55
64
|
-h, --help display help for command
|
|
56
65
|
|
|
@@ -82,9 +91,27 @@ for (let i = 2, l = argv.length; i < l; ++i) {
|
|
|
82
91
|
case 'F':
|
|
83
92
|
params.config = false
|
|
84
93
|
return
|
|
94
|
+
case 'ignore-proto-key':
|
|
95
|
+
params.ignoreProtoKey = flag
|
|
96
|
+
return
|
|
97
|
+
case 'ignore-prototype-keys':
|
|
98
|
+
params.ignorePrototypeKeys = flag
|
|
99
|
+
return
|
|
85
100
|
case 's': case 'sort-keys':
|
|
86
101
|
params.sortKeys = flag
|
|
87
102
|
return
|
|
103
|
+
case 'sort-keys-ignore-case':
|
|
104
|
+
params.sortKeysIgnoreCase = flag
|
|
105
|
+
return
|
|
106
|
+
case 'sort-keys-locale':
|
|
107
|
+
params.sortKeysLocale = match[4] || argv[++i]
|
|
108
|
+
return
|
|
109
|
+
case 'sort-keys-case-first':
|
|
110
|
+
params.sortKeysCaseFirst = match[4] || argv[++i]
|
|
111
|
+
return
|
|
112
|
+
case 'sort-keys-numeric':
|
|
113
|
+
params.sortKeysNumeric = flag
|
|
114
|
+
return
|
|
88
115
|
case 'E': case 'extensions':
|
|
89
116
|
arg = match[4] || argv[++i]
|
|
90
117
|
params.extensions.push(...arg.split(','))
|
|
@@ -100,7 +127,7 @@ for (let i = 2, l = argv.length; i < l; ++i) {
|
|
|
100
127
|
return
|
|
101
128
|
case 't': case 'indent':
|
|
102
129
|
arg = match[4] || argv[++i]
|
|
103
|
-
if (arg.trim().length > 0 && !isNaN(+arg)) arg = +arg
|
|
130
|
+
if (arg.trim().length > 0 && !Number.isNaN(+arg)) arg = +arg
|
|
104
131
|
params.indent = arg
|
|
105
132
|
return
|
|
106
133
|
case 'c': case 'compact':
|
|
@@ -149,7 +176,7 @@ for (let i = 2, l = argv.length; i < l; ++i) {
|
|
|
149
176
|
return
|
|
150
177
|
case 'x': case 'context':
|
|
151
178
|
arg = match[4] || argv[++i]
|
|
152
|
-
if (isNaN(+arg)) {
|
|
179
|
+
if (Number.isNaN(+arg)) {
|
|
153
180
|
throw new Error(`invalid diff context: "${arg}"`)
|
|
154
181
|
}
|
|
155
182
|
params.indent = +arg
|
|
@@ -190,6 +217,9 @@ for (let i = 2, l = argv.length; i < l; ++i) {
|
|
|
190
217
|
case 'trim-trailing-commas':
|
|
191
218
|
params.trimTrailingCommas = flag
|
|
192
219
|
return
|
|
220
|
+
case 'succeed-with-no-files':
|
|
221
|
+
params.succeedWithNoFiles = flag
|
|
222
|
+
return
|
|
193
223
|
case 'v': case 'version':
|
|
194
224
|
console.log(require('../package.json').version)
|
|
195
225
|
process.exit(0)
|
|
@@ -216,6 +246,8 @@ for (let i = 2, l = argv.length; i < l; ++i) {
|
|
|
216
246
|
}
|
|
217
247
|
|
|
218
248
|
const paramNames = {
|
|
249
|
+
'ignore-proto-key': 'ignoreProtoKey',
|
|
250
|
+
'ignore-prototype-keys': 'ignorePrototypeKeys',
|
|
219
251
|
'trailing-commas': 'trailingCommas',
|
|
220
252
|
'single-quoted-strings': 'singleQuotedStrings',
|
|
221
253
|
'duplicate-keys': 'duplicateKeys',
|
|
@@ -226,6 +258,10 @@ const paramNames = {
|
|
|
226
258
|
'enforce-single-quotes': 'enforceSingleQuotes',
|
|
227
259
|
'trim-trailing-commas': 'trimTrailingCommas',
|
|
228
260
|
'sort-keys': 'sortKeys',
|
|
261
|
+
'sort-keys-ignore-case': 'sortKeysIgnoreCase',
|
|
262
|
+
'sort-keys-locale': 'sortKeysLocale',
|
|
263
|
+
'sort-keys-case-first': 'sortKeysCaseFirst',
|
|
264
|
+
'sort-keys-numeric': 'sortKeysNumeric',
|
|
229
265
|
'pretty-print-invalid': 'prettyPrintInvalid',
|
|
230
266
|
'log-files': 'logFiles',
|
|
231
267
|
'in-place': 'inPlace',
|
|
@@ -283,20 +319,23 @@ function logNormalError (error, file) {
|
|
|
283
319
|
}
|
|
284
320
|
|
|
285
321
|
function logCompactError (error, file) {
|
|
286
|
-
console.error(file
|
|
287
|
-
', col ' + error.location.start.column + ', ' + error.reason + '.')
|
|
322
|
+
console.error(`${file}: line ${error.location.start.line}, col ${error.location.start.column}, ${error.reason}.`)
|
|
288
323
|
}
|
|
289
324
|
|
|
290
325
|
function processContents (source, file) {
|
|
291
|
-
let parserOptions
|
|
326
|
+
let parserOptions
|
|
327
|
+
let parsed
|
|
328
|
+
let formatted
|
|
292
329
|
try {
|
|
293
330
|
parserOptions = {
|
|
294
331
|
mode: params.mode,
|
|
295
332
|
ignoreBOM: params.bom,
|
|
296
333
|
ignoreComments: params.comments,
|
|
297
|
-
ignoreTrailingCommas: params.trailingCommas,
|
|
334
|
+
ignoreTrailingCommas: params.trailingCommas || params.trimTrailingCommas,
|
|
298
335
|
allowSingleQuotedStrings: params.singleQuotedStrings,
|
|
299
|
-
allowDuplicateObjectKeys: params.duplicateKeys
|
|
336
|
+
allowDuplicateObjectKeys: params.duplicateKeys,
|
|
337
|
+
ignoreProtoKey: params.ignoreProtoKey,
|
|
338
|
+
ignorePrototypeKeys: params.ignorePrototypeKeys
|
|
300
339
|
}
|
|
301
340
|
if (params.validate.length) {
|
|
302
341
|
const schemas = params.validate.map((file, index) => {
|
|
@@ -329,8 +368,29 @@ function processContents (source, file) {
|
|
|
329
368
|
trimTrailingCommas: params.trimTrailingCommas
|
|
330
369
|
})
|
|
331
370
|
}
|
|
371
|
+
const sortOptions = {}
|
|
372
|
+
let sort
|
|
332
373
|
if (params.sortKeys) {
|
|
333
|
-
|
|
374
|
+
sort = true
|
|
375
|
+
}
|
|
376
|
+
if (params.sortKeysIgnoreCase) {
|
|
377
|
+
sortOptions.ignoreCase = true
|
|
378
|
+
sort = true
|
|
379
|
+
}
|
|
380
|
+
if (params.sortKeysLocale) {
|
|
381
|
+
sortOptions.locale = params.sortKeysLocale
|
|
382
|
+
sort = true
|
|
383
|
+
}
|
|
384
|
+
if (params.sortKeysCaseFirst) {
|
|
385
|
+
sortOptions.caseFirst = params.sortKeysCaseFirst
|
|
386
|
+
sort = true
|
|
387
|
+
}
|
|
388
|
+
if (params.sortKeysNumeric) {
|
|
389
|
+
sortOptions.numeric = true
|
|
390
|
+
sort = true
|
|
391
|
+
}
|
|
392
|
+
if (sort) {
|
|
393
|
+
parsed = sortObject(parsed, sortOptions)
|
|
334
394
|
}
|
|
335
395
|
return JSON.stringify(parsed, null, params.indent)
|
|
336
396
|
} catch (e) {
|
|
@@ -381,7 +441,7 @@ function ensureLineBreak (parsed, source) {
|
|
|
381
441
|
function checkContents (file, source, parsed) {
|
|
382
442
|
const { createTwoFilesPatch, structuredPatch } = require('diff')
|
|
383
443
|
const structured = structuredPatch(`${file}.orig`, file, source, parsed, '', '', { context: params.context })
|
|
384
|
-
const length = structured.hunks
|
|
444
|
+
const length = structured.hunks?.length
|
|
385
445
|
if (length > 0) {
|
|
386
446
|
const hunk = length === 1 ? 'hunk differs' : 'hunks differ'
|
|
387
447
|
const message = `${length} ${hunk}`
|
|
@@ -413,10 +473,11 @@ function checkContents (file, source, parsed) {
|
|
|
413
473
|
function diffContents (file, source, parsed) {
|
|
414
474
|
const { createTwoFilesPatch, structuredPatch } = require('diff')
|
|
415
475
|
const compact = params.quiet || params.compact
|
|
416
|
-
let diff
|
|
476
|
+
let diff
|
|
477
|
+
let length
|
|
417
478
|
if (compact) {
|
|
418
479
|
diff = structuredPatch(`${file}.orig`, file, source, parsed, '', '', { context: params.context })
|
|
419
|
-
length = diff.hunks
|
|
480
|
+
length = diff.hunks?.length
|
|
420
481
|
} else {
|
|
421
482
|
diff = createTwoFilesPatch(`${file}.orig`, file, source, parsed, '', '', { context: params.context })
|
|
422
483
|
length = diff.split(/\r?\n/).length - 4
|
|
@@ -487,7 +548,7 @@ function processPatterns (patterns) {
|
|
|
487
548
|
const files = sync(patterns, { onlyFiles: true })
|
|
488
549
|
if (!files.length) {
|
|
489
550
|
console.error('no files found')
|
|
490
|
-
process.exit(1)
|
|
551
|
+
process.exit(params.succeedWithNoFiles ? 0 : 1)
|
|
491
552
|
}
|
|
492
553
|
for (const file of files) {
|
|
493
554
|
try {
|
package/lib/formatter.js
CHANGED
|
@@ -36,7 +36,7 @@
|
|
|
36
36
|
case '{':
|
|
37
37
|
case '[':
|
|
38
38
|
if (!inString) {
|
|
39
|
-
outputString += currentChar
|
|
39
|
+
outputString += `${currentChar}\n${repeat(indentString, indentLevel + 1)}`
|
|
40
40
|
indentLevel += 1
|
|
41
41
|
} else {
|
|
42
42
|
outputString += currentChar
|
|
@@ -46,14 +46,14 @@
|
|
|
46
46
|
case ']':
|
|
47
47
|
if (!inString) {
|
|
48
48
|
indentLevel -= 1
|
|
49
|
-
outputString +=
|
|
49
|
+
outputString += `\n${repeat(indentString, indentLevel)}${currentChar}`
|
|
50
50
|
} else {
|
|
51
51
|
outputString += currentChar
|
|
52
52
|
}
|
|
53
53
|
break
|
|
54
54
|
case ',':
|
|
55
55
|
if (!inString) {
|
|
56
|
-
outputString +=
|
|
56
|
+
outputString += `,\n${repeat(indentString, indentLevel)}`
|
|
57
57
|
} else {
|
|
58
58
|
outputString += currentChar
|
|
59
59
|
}
|