eslint-plugin-package-json 0.33.1 → 0.34.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/CHANGELOG.md +14 -2
- package/lib/index.d.mts +6 -2
- package/lib/index.d.ts +6 -2
- package/lib/plugin.d.mts +6 -2
- package/lib/plugin.d.ts +6 -2
- package/lib/plugin.js +21 -3
- package/lib/plugin.mjs +21 -3
- package/lib/rules/no-redundant-files.js +5 -1
- package/lib/rules/no-redundant-files.mjs +5 -1
- package/lib/rules/valid-package-definition.d.mts +5 -1
- package/lib/rules/valid-package-definition.d.ts +5 -1
- package/lib/rules/valid-package-definition.js +22 -5
- package/lib/rules/valid-package-definition.mjs +22 -5
- package/package.json +12 -12
package/CHANGELOG.md
CHANGED
|
@@ -1,11 +1,23 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
# [0.34.0](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/compare/v0.33.2...v0.34.0) (2025-06-10)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### Features
|
|
7
|
+
|
|
8
|
+
* **valid-package-definition:** add ignoreProperties option ([#1077](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1077)) ([530e343](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/commit/530e3430f87f21c9fadd4d511097d20e26f7190f)), closes [#1076](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1076)
|
|
4
9
|
|
|
10
|
+
## [0.33.2](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/compare/v0.33.1...v0.33.2) (2025-06-01)
|
|
11
|
+
|
|
12
|
+
### Bug Fixes
|
|
13
|
+
|
|
14
|
+
- prevent `no-redundant-files` crash with wildcard and `main` field ([#1078](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1078)) ([ad4f95f](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/commit/ad4f95f382bce8d5d0ecc79e4242596dc3eec771)), closes [#1066](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1066)
|
|
15
|
+
|
|
16
|
+
## [0.33.1](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/compare/v0.33.0...v0.33.1) (2025-06-01)
|
|
5
17
|
|
|
6
18
|
### Bug Fixes
|
|
7
19
|
|
|
8
|
-
|
|
20
|
+
- add CHANGELOG to package ([#1075](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1075)) ([eb13030](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/commit/eb130302b6dfcc456dfeaf49fdfd61bd4fa495d1)), closes [#1070](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/issues/1070)
|
|
9
21
|
|
|
10
22
|
# [0.33.0](https://github.com/JoshuaKGoldberg/eslint-plugin-package-json/compare/v0.32.0...v0.33.0) (2025-05-31)
|
|
11
23
|
|
package/lib/index.d.mts
CHANGED
|
@@ -9,7 +9,9 @@ declare const configs: {
|
|
|
9
9
|
"legacy-recommended": {
|
|
10
10
|
plugins: string[];
|
|
11
11
|
rules: {
|
|
12
|
-
|
|
12
|
+
"package-json/valid-package-definition": ["error", {
|
|
13
|
+
ignoreProperties: string[];
|
|
14
|
+
}];
|
|
13
15
|
};
|
|
14
16
|
};
|
|
15
17
|
recommended: {
|
|
@@ -29,7 +31,9 @@ declare const configs: {
|
|
|
29
31
|
};
|
|
30
32
|
};
|
|
31
33
|
rules: {
|
|
32
|
-
|
|
34
|
+
"package-json/valid-package-definition": ["error", {
|
|
35
|
+
ignoreProperties: string[];
|
|
36
|
+
}];
|
|
33
37
|
};
|
|
34
38
|
};
|
|
35
39
|
};
|
package/lib/index.d.ts
CHANGED
|
@@ -9,7 +9,9 @@ declare const configs: {
|
|
|
9
9
|
"legacy-recommended": {
|
|
10
10
|
plugins: string[];
|
|
11
11
|
rules: {
|
|
12
|
-
|
|
12
|
+
"package-json/valid-package-definition": ["error", {
|
|
13
|
+
ignoreProperties: string[];
|
|
14
|
+
}];
|
|
13
15
|
};
|
|
14
16
|
};
|
|
15
17
|
recommended: {
|
|
@@ -29,7 +31,9 @@ declare const configs: {
|
|
|
29
31
|
};
|
|
30
32
|
};
|
|
31
33
|
rules: {
|
|
32
|
-
|
|
34
|
+
"package-json/valid-package-definition": ["error", {
|
|
35
|
+
ignoreProperties: string[];
|
|
36
|
+
}];
|
|
33
37
|
};
|
|
34
38
|
};
|
|
35
39
|
};
|
package/lib/plugin.d.mts
CHANGED
|
@@ -8,7 +8,9 @@ declare const plugin: {
|
|
|
8
8
|
"legacy-recommended": {
|
|
9
9
|
plugins: string[];
|
|
10
10
|
rules: {
|
|
11
|
-
|
|
11
|
+
"package-json/valid-package-definition": ["error", {
|
|
12
|
+
ignoreProperties: string[];
|
|
13
|
+
}];
|
|
12
14
|
};
|
|
13
15
|
};
|
|
14
16
|
recommended: {
|
|
@@ -21,7 +23,9 @@ declare const plugin: {
|
|
|
21
23
|
readonly "package-json": /*elided*/ any;
|
|
22
24
|
};
|
|
23
25
|
rules: {
|
|
24
|
-
|
|
26
|
+
"package-json/valid-package-definition": ["error", {
|
|
27
|
+
ignoreProperties: string[];
|
|
28
|
+
}];
|
|
25
29
|
};
|
|
26
30
|
};
|
|
27
31
|
};
|
package/lib/plugin.d.ts
CHANGED
|
@@ -8,7 +8,9 @@ declare const plugin: {
|
|
|
8
8
|
"legacy-recommended": {
|
|
9
9
|
plugins: string[];
|
|
10
10
|
rules: {
|
|
11
|
-
|
|
11
|
+
"package-json/valid-package-definition": ["error", {
|
|
12
|
+
ignoreProperties: string[];
|
|
13
|
+
}];
|
|
12
14
|
};
|
|
13
15
|
};
|
|
14
16
|
recommended: {
|
|
@@ -21,7 +23,9 @@ declare const plugin: {
|
|
|
21
23
|
readonly "package-json": /*elided*/ any;
|
|
22
24
|
};
|
|
23
25
|
rules: {
|
|
24
|
-
|
|
26
|
+
"package-json/valid-package-definition": ["error", {
|
|
27
|
+
ignoreProperties: string[];
|
|
28
|
+
}];
|
|
25
29
|
};
|
|
26
30
|
};
|
|
27
31
|
};
|
package/lib/plugin.js
CHANGED
|
@@ -77,9 +77,27 @@ const rules = {
|
|
|
77
77
|
}
|
|
78
78
|
}
|
|
79
79
|
};
|
|
80
|
-
const
|
|
81
|
-
Object.
|
|
82
|
-
)
|
|
80
|
+
const baseRecommendedRules = {
|
|
81
|
+
...Object.fromEntries(
|
|
82
|
+
Object.entries(rules).filter(([, rule]) => rule.meta.docs?.recommended).map(([name2]) => ["package-json/" + name2, "error"])
|
|
83
|
+
)
|
|
84
|
+
};
|
|
85
|
+
const recommendedRules = {
|
|
86
|
+
...baseRecommendedRules,
|
|
87
|
+
// As we add more `valid-*` rules, we should prevent this legacy rule from
|
|
88
|
+
// also reporting the same errors.
|
|
89
|
+
"package-json/valid-package-definition": [
|
|
90
|
+
"error",
|
|
91
|
+
{
|
|
92
|
+
// Create a list of properties to ignore based on the valid-* rules
|
|
93
|
+
// we currently have. Once we've fully covered what `valid-package-definition`
|
|
94
|
+
// checks, we can remove it from the `recommended` config entirely.
|
|
95
|
+
ignoreProperties: Object.entries(baseRecommendedRules).filter(
|
|
96
|
+
([name2]) => name2.startsWith("package-json/valid-") && name2 !== "package-json/valid-package-definition"
|
|
97
|
+
).map(([name2]) => name2.replace("package-json/valid-", ""))
|
|
98
|
+
}
|
|
99
|
+
]
|
|
100
|
+
};
|
|
83
101
|
const plugin = {
|
|
84
102
|
configs: {
|
|
85
103
|
"legacy-recommended": {
|
package/lib/plugin.mjs
CHANGED
|
@@ -43,9 +43,27 @@ const rules = {
|
|
|
43
43
|
}
|
|
44
44
|
}
|
|
45
45
|
};
|
|
46
|
-
const
|
|
47
|
-
Object.
|
|
48
|
-
)
|
|
46
|
+
const baseRecommendedRules = {
|
|
47
|
+
...Object.fromEntries(
|
|
48
|
+
Object.entries(rules).filter(([, rule]) => rule.meta.docs?.recommended).map(([name2]) => ["package-json/" + name2, "error"])
|
|
49
|
+
)
|
|
50
|
+
};
|
|
51
|
+
const recommendedRules = {
|
|
52
|
+
...baseRecommendedRules,
|
|
53
|
+
// As we add more `valid-*` rules, we should prevent this legacy rule from
|
|
54
|
+
// also reporting the same errors.
|
|
55
|
+
"package-json/valid-package-definition": [
|
|
56
|
+
"error",
|
|
57
|
+
{
|
|
58
|
+
// Create a list of properties to ignore based on the valid-* rules
|
|
59
|
+
// we currently have. Once we've fully covered what `valid-package-definition`
|
|
60
|
+
// checks, we can remove it from the `recommended` config entirely.
|
|
61
|
+
ignoreProperties: Object.entries(baseRecommendedRules).filter(
|
|
62
|
+
([name2]) => name2.startsWith("package-json/valid-") && name2 !== "package-json/valid-package-definition"
|
|
63
|
+
).map(([name2]) => name2.replace("package-json/valid-", ""))
|
|
64
|
+
}
|
|
65
|
+
]
|
|
66
|
+
};
|
|
49
67
|
const plugin = {
|
|
50
68
|
configs: {
|
|
51
69
|
"legacy-recommended": {
|
|
@@ -30,8 +30,12 @@ const defaultFiles = [
|
|
|
30
30
|
/^(\.\/)?README(\.|$)/i,
|
|
31
31
|
/^(\.\/)?package\.json$/i
|
|
32
32
|
];
|
|
33
|
+
const wildcardsRegex = /[*?[\]{}]/;
|
|
33
34
|
const cachedRegex = /* @__PURE__ */ new Map();
|
|
34
35
|
const getCachedLocalFileRegex = (filename) => {
|
|
36
|
+
if (wildcardsRegex.test(filename)) {
|
|
37
|
+
return null;
|
|
38
|
+
}
|
|
35
39
|
const baseFilename = filename.replace("./", "");
|
|
36
40
|
let regex = cachedRegex.get(baseFilename);
|
|
37
41
|
if (regex) {
|
|
@@ -132,7 +136,7 @@ const rule = (0, import_createRule.createRule)({
|
|
|
132
136
|
const regex = getCachedLocalFileRegex(
|
|
133
137
|
fileEntry.value
|
|
134
138
|
);
|
|
135
|
-
if (regex
|
|
139
|
+
if (regex?.test(fileToCheck)) {
|
|
136
140
|
report(files, index, validation.messageId);
|
|
137
141
|
}
|
|
138
142
|
}
|
|
@@ -7,8 +7,12 @@ const defaultFiles = [
|
|
|
7
7
|
/^(\.\/)?README(\.|$)/i,
|
|
8
8
|
/^(\.\/)?package\.json$/i
|
|
9
9
|
];
|
|
10
|
+
const wildcardsRegex = /[*?[\]{}]/;
|
|
10
11
|
const cachedRegex = /* @__PURE__ */ new Map();
|
|
11
12
|
const getCachedLocalFileRegex = (filename) => {
|
|
13
|
+
if (wildcardsRegex.test(filename)) {
|
|
14
|
+
return null;
|
|
15
|
+
}
|
|
12
16
|
const baseFilename = filename.replace("./", "");
|
|
13
17
|
let regex = cachedRegex.get(baseFilename);
|
|
14
18
|
if (regex) {
|
|
@@ -109,7 +113,7 @@ const rule = createRule({
|
|
|
109
113
|
const regex = getCachedLocalFileRegex(
|
|
110
114
|
fileEntry.value
|
|
111
115
|
);
|
|
112
|
-
if (regex
|
|
116
|
+
if (regex?.test(fileToCheck)) {
|
|
113
117
|
report(files, index, validation.messageId);
|
|
114
118
|
}
|
|
115
119
|
}
|
|
@@ -3,8 +3,12 @@ import * as jsonc_eslint_parser from 'jsonc-eslint-parser';
|
|
|
3
3
|
import { PackageJsonRuleContext } from '../createRule.mjs';
|
|
4
4
|
import 'estree';
|
|
5
5
|
|
|
6
|
+
interface Option {
|
|
7
|
+
ignoreProperties?: string[];
|
|
8
|
+
}
|
|
9
|
+
type Options = [Option?];
|
|
6
10
|
declare const rule: {
|
|
7
|
-
create(context: PackageJsonRuleContext<
|
|
11
|
+
create(context: PackageJsonRuleContext<Options>): jsonc_eslint_parser.RuleListener;
|
|
8
12
|
meta: eslint.Rule.RuleMetaData;
|
|
9
13
|
};
|
|
10
14
|
|
|
@@ -3,8 +3,12 @@ import * as jsonc_eslint_parser from 'jsonc-eslint-parser';
|
|
|
3
3
|
import { PackageJsonRuleContext } from '../createRule.js';
|
|
4
4
|
import 'estree';
|
|
5
5
|
|
|
6
|
+
interface Option {
|
|
7
|
+
ignoreProperties?: string[];
|
|
8
|
+
}
|
|
9
|
+
type Options = [Option?];
|
|
6
10
|
declare const rule: {
|
|
7
|
-
create(context: PackageJsonRuleContext<
|
|
11
|
+
create(context: PackageJsonRuleContext<Options>): jsonc_eslint_parser.RuleListener;
|
|
8
12
|
meta: eslint.Rule.RuleMetaData;
|
|
9
13
|
};
|
|
10
14
|
|
|
@@ -31,18 +31,22 @@ const ignoredErrors = [
|
|
|
31
31
|
const isUsableError = (errorText) => ignoredErrors.every((pattern) => !pattern.test(errorText));
|
|
32
32
|
const rule = (0, import_createRule.createRule)({
|
|
33
33
|
create(context) {
|
|
34
|
+
const ignoreProperties = context.options[0]?.ignoreProperties ?? [];
|
|
34
35
|
return {
|
|
35
36
|
"Program:exit"() {
|
|
36
37
|
const validation = (0, import_package_json_validator.validate)(context.sourceCode.text);
|
|
37
|
-
validation.errors?.filter(
|
|
38
|
-
|
|
38
|
+
const usableErrors = validation.errors?.filter((error) => {
|
|
39
|
+
return isUsableError(error.message) && !ignoreProperties.includes(error.field);
|
|
40
|
+
}) ?? [];
|
|
41
|
+
for (const error of usableErrors) {
|
|
42
|
+
if (error.message) {
|
|
39
43
|
context.report({
|
|
40
44
|
// eslint-disable-next-line eslint-plugin/prefer-message-ids
|
|
41
|
-
message,
|
|
45
|
+
message: error.message,
|
|
42
46
|
node: context.sourceCode.ast
|
|
43
47
|
});
|
|
44
48
|
}
|
|
45
|
-
}
|
|
49
|
+
}
|
|
46
50
|
}
|
|
47
51
|
};
|
|
48
52
|
},
|
|
@@ -53,7 +57,20 @@ const rule = (0, import_createRule.createRule)({
|
|
|
53
57
|
description: "Enforce that package.json has all properties required by the npm spec",
|
|
54
58
|
recommended: true
|
|
55
59
|
},
|
|
56
|
-
schema: [
|
|
60
|
+
schema: [
|
|
61
|
+
{
|
|
62
|
+
additionalProperties: false,
|
|
63
|
+
properties: {
|
|
64
|
+
ignoreProperties: {
|
|
65
|
+
items: {
|
|
66
|
+
type: "string"
|
|
67
|
+
},
|
|
68
|
+
type: "array"
|
|
69
|
+
}
|
|
70
|
+
},
|
|
71
|
+
type: "object"
|
|
72
|
+
}
|
|
73
|
+
],
|
|
57
74
|
type: "problem"
|
|
58
75
|
}
|
|
59
76
|
});
|
|
@@ -8,18 +8,22 @@ const ignoredErrors = [
|
|
|
8
8
|
const isUsableError = (errorText) => ignoredErrors.every((pattern) => !pattern.test(errorText));
|
|
9
9
|
const rule = createRule({
|
|
10
10
|
create(context) {
|
|
11
|
+
const ignoreProperties = context.options[0]?.ignoreProperties ?? [];
|
|
11
12
|
return {
|
|
12
13
|
"Program:exit"() {
|
|
13
14
|
const validation = validate(context.sourceCode.text);
|
|
14
|
-
validation.errors?.filter(
|
|
15
|
-
|
|
15
|
+
const usableErrors = validation.errors?.filter((error) => {
|
|
16
|
+
return isUsableError(error.message) && !ignoreProperties.includes(error.field);
|
|
17
|
+
}) ?? [];
|
|
18
|
+
for (const error of usableErrors) {
|
|
19
|
+
if (error.message) {
|
|
16
20
|
context.report({
|
|
17
21
|
// eslint-disable-next-line eslint-plugin/prefer-message-ids
|
|
18
|
-
message,
|
|
22
|
+
message: error.message,
|
|
19
23
|
node: context.sourceCode.ast
|
|
20
24
|
});
|
|
21
25
|
}
|
|
22
|
-
}
|
|
26
|
+
}
|
|
23
27
|
}
|
|
24
28
|
};
|
|
25
29
|
},
|
|
@@ -30,7 +34,20 @@ const rule = createRule({
|
|
|
30
34
|
description: "Enforce that package.json has all properties required by the npm spec",
|
|
31
35
|
recommended: true
|
|
32
36
|
},
|
|
33
|
-
schema: [
|
|
37
|
+
schema: [
|
|
38
|
+
{
|
|
39
|
+
additionalProperties: false,
|
|
40
|
+
properties: {
|
|
41
|
+
ignoreProperties: {
|
|
42
|
+
items: {
|
|
43
|
+
type: "string"
|
|
44
|
+
},
|
|
45
|
+
type: "array"
|
|
46
|
+
}
|
|
47
|
+
},
|
|
48
|
+
type: "object"
|
|
49
|
+
}
|
|
50
|
+
],
|
|
34
51
|
type: "problem"
|
|
35
52
|
}
|
|
36
53
|
});
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "eslint-plugin-package-json",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.34.0",
|
|
4
4
|
"description": "Rules for consistent, readable, and valid package.json files. 🗂️",
|
|
5
5
|
"homepage": "https://github.com/JoshuaKGoldberg/eslint-plugin-package-json#readme",
|
|
6
6
|
"bugs": {
|
|
@@ -43,7 +43,7 @@
|
|
|
43
43
|
"lint:spelling": "cspell \"**\" \".github/**/*\"",
|
|
44
44
|
"prepare": "husky",
|
|
45
45
|
"test": "vitest",
|
|
46
|
-
"
|
|
46
|
+
"typecheck": "tsc"
|
|
47
47
|
},
|
|
48
48
|
"lint-staged": {
|
|
49
49
|
"*": "prettier --ignore-unknown --write"
|
|
@@ -53,7 +53,7 @@
|
|
|
53
53
|
"detect-indent": "6.1.0",
|
|
54
54
|
"detect-newline": "3.1.0",
|
|
55
55
|
"eslint-fix-utils": "^0.2.0",
|
|
56
|
-
"package-json-validator": "
|
|
56
|
+
"package-json-validator": "~0.13.1",
|
|
57
57
|
"semver": "^7.5.4",
|
|
58
58
|
"sort-object-keys": "^1.1.3",
|
|
59
59
|
"sort-package-json": "^3.0.0",
|
|
@@ -61,7 +61,7 @@
|
|
|
61
61
|
},
|
|
62
62
|
"devDependencies": {
|
|
63
63
|
"@eslint-community/eslint-plugin-eslint-comments": "4.5.0",
|
|
64
|
-
"@eslint/js": "9.
|
|
64
|
+
"@eslint/js": "9.28.0",
|
|
65
65
|
"@release-it/conventional-changelog": "10.0.0",
|
|
66
66
|
"@types/eslint-plugin-markdown": "2.0.2",
|
|
67
67
|
"@types/estree": "1.0.7",
|
|
@@ -69,25 +69,25 @@
|
|
|
69
69
|
"@types/semver": "7.7.0",
|
|
70
70
|
"@types/sort-object-keys": "1.1.3",
|
|
71
71
|
"@types/validate-npm-package-name": "4.0.2",
|
|
72
|
-
"@vitest/coverage-v8": "3.
|
|
72
|
+
"@vitest/coverage-v8": "3.2.0",
|
|
73
73
|
"@vitest/eslint-plugin": "1.2.0",
|
|
74
74
|
"console-fail-test": "0.5.0",
|
|
75
75
|
"create-typescript-app": "2.42.0",
|
|
76
76
|
"cspell": "8.19.0",
|
|
77
|
-
"eslint": "9.
|
|
77
|
+
"eslint": "9.28.0",
|
|
78
78
|
"eslint-doc-generator": "2.1.2",
|
|
79
79
|
"eslint-plugin-eslint-plugin": "6.4.0",
|
|
80
|
-
"eslint-plugin-jsdoc": "50.
|
|
80
|
+
"eslint-plugin-jsdoc": "50.7.0",
|
|
81
81
|
"eslint-plugin-jsonc": "2.20.0",
|
|
82
82
|
"eslint-plugin-markdown": "5.1.0",
|
|
83
|
-
"eslint-plugin-n": "17.
|
|
83
|
+
"eslint-plugin-n": "17.19.0",
|
|
84
84
|
"eslint-plugin-perfectionist": "4.13.0",
|
|
85
85
|
"eslint-plugin-regexp": "2.7.0",
|
|
86
86
|
"eslint-plugin-yml": "1.18.0",
|
|
87
87
|
"husky": "9.1.7",
|
|
88
88
|
"jsonc-eslint-parser": "2.4.0",
|
|
89
|
-
"knip": "5.
|
|
90
|
-
"lint-staged": "16.
|
|
89
|
+
"knip": "5.59.0",
|
|
90
|
+
"lint-staged": "16.1.0",
|
|
91
91
|
"markdownlint": "0.38.0",
|
|
92
92
|
"markdownlint-cli": "0.45.0",
|
|
93
93
|
"prettier": "3.5.3",
|
|
@@ -98,8 +98,8 @@
|
|
|
98
98
|
"sentences-per-line": "0.3.0",
|
|
99
99
|
"tsup": "8.5.0",
|
|
100
100
|
"typescript": "5.8.2",
|
|
101
|
-
"typescript-eslint": "8.
|
|
102
|
-
"vitest": "3.
|
|
101
|
+
"typescript-eslint": "8.33.0",
|
|
102
|
+
"vitest": "3.2.0"
|
|
103
103
|
},
|
|
104
104
|
"peerDependencies": {
|
|
105
105
|
"eslint": ">=8.0.0",
|