@plugjs/eslint-plugin 0.1.23 → 0.2.0-beta.2
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/README.md +46 -10
- package/bundles/eslint-import-resolver-node.cjs +64 -0
- package/bundles/eslint-import-resolver-typescript.cjs +277 -0
- package/bundles/eslint-plugin-import-x.cjs +8022 -0
- package/bundles/stylistic-eslint-plugin.cjs +20708 -0
- package/configs/basic.mjs +187 -0
- package/configs/javascript.mjs +51 -0
- package/configs/typescript.mjs +51 -0
- package/eslint.config.mjs +40 -0
- package/package.json +34 -14
- package/configs/typescript.cjs +0 -192
- package/index.cjs +0 -5
package/README.md
CHANGED
|
@@ -1,19 +1,55 @@
|
|
|
1
|
-
PlugJS ESLint Shared Configuration
|
|
2
|
-
|
|
1
|
+
PlugJS ESLint (v9) Shared Configuration
|
|
2
|
+
=======================================
|
|
3
3
|
|
|
4
|
-
This package exports simple configurations for linting our
|
|
4
|
+
This package exports simple configurations for linting our projects. It's the
|
|
5
5
|
easiest way to actually share some configs and plugins.
|
|
6
6
|
|
|
7
|
-
Just add in your
|
|
7
|
+
Just add in your `eslint.config.mjs` something similar to:
|
|
8
8
|
|
|
9
9
|
```javascript
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
10
|
+
import configurations from '@plugjs/eslint-plugin'
|
|
11
|
+
|
|
12
|
+
export default [
|
|
13
|
+
...configurations,
|
|
14
|
+
// any other configuration you might want to add for your project...
|
|
15
|
+
]
|
|
16
16
|
```
|
|
17
17
|
|
|
18
|
+
This includes a number of configurations:
|
|
19
|
+
|
|
20
|
+
* `eslint-recommended`: recommended JavaScript config from ESLint.
|
|
21
|
+
|
|
22
|
+
* `plugjs-base`: basic configuration of ESLint rules.
|
|
23
|
+
* `plugjs-stylistic`: style shared between JavaScript and TypeScript.
|
|
24
|
+
* `plugjs-unicorn`: extra niceties from the ESLint Unicorn plugin.
|
|
25
|
+
* `plugjs-importx`: defines the style of our imports.
|
|
26
|
+
|
|
27
|
+
* `plugjs-javascript`: basic extra rules for JavaScript sources.
|
|
28
|
+
* `plugjs-javascript-cjs`: marks `*.cjs` files as `commonjs`.
|
|
29
|
+
* `plugjs-javascript-mjs`: marks `*.mjs` files as `module`.
|
|
30
|
+
|
|
31
|
+
* `typescript-eslint/recommended`: imports all the configurations from
|
|
32
|
+
TypeScript ESlint recommended, but restrict them to operate only on
|
|
33
|
+
`.ts`, `.cts`, and `.mts` files. This *should* include:
|
|
34
|
+
* `typescript-eslint/base`: basic parser configuration.
|
|
35
|
+
* `typescript-eslint/eslint-recommended`: disable ESLint rules conflicting
|
|
36
|
+
with TypeScript.
|
|
37
|
+
* `typescript-eslint/recommended`: recommended config for TypeScript
|
|
38
|
+
* `plugjs-typescript`: our rules overriding `typescript-eslint/recommended`.
|
|
39
|
+
|
|
40
|
+
Notes on building
|
|
41
|
+
-----------------
|
|
42
|
+
|
|
43
|
+
During this transitional period (ESLint from v8 to v9, and TypeScript ESLint
|
|
44
|
+
from v7 to v8) a number of plugins, even if they are working, are specifying
|
|
45
|
+
wrong/old dependencies in their packages.
|
|
46
|
+
|
|
47
|
+
For those plugins, we bundle them up and ship them with this plugin, and
|
|
48
|
+
hopefully we'll be able to un-bundle them as the various packages move in their
|
|
49
|
+
transitions.
|
|
50
|
+
|
|
51
|
+
Legal Stuff
|
|
52
|
+
-----------
|
|
53
|
+
|
|
18
54
|
* [Copyright Notice](NOTICE.md)
|
|
19
55
|
* [License](LICENSE.md)
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
// node_modules/eslint-import-resolver-node/index.js
|
|
4
|
+
var resolve = require("resolve/sync");
|
|
5
|
+
var isCoreModule = require("is-core-module");
|
|
6
|
+
var path = require("path");
|
|
7
|
+
var log = require("debug")("eslint-plugin-import:resolver:node");
|
|
8
|
+
exports.interfaceVersion = 2;
|
|
9
|
+
exports.resolve = function(source, file, config) {
|
|
10
|
+
log("Resolving:", source, "from:", file);
|
|
11
|
+
let resolvedPath;
|
|
12
|
+
if (isCoreModule(source)) {
|
|
13
|
+
log("resolved to core");
|
|
14
|
+
return { found: true, path: null };
|
|
15
|
+
}
|
|
16
|
+
try {
|
|
17
|
+
const cachedFilter = function(pkg, dir) {
|
|
18
|
+
return packageFilter(pkg, dir, config);
|
|
19
|
+
};
|
|
20
|
+
resolvedPath = resolve(source, opts(file, config, cachedFilter));
|
|
21
|
+
log("Resolved to:", resolvedPath);
|
|
22
|
+
return { found: true, path: resolvedPath };
|
|
23
|
+
} catch (err) {
|
|
24
|
+
log("resolve threw error:", err);
|
|
25
|
+
return { found: false };
|
|
26
|
+
}
|
|
27
|
+
};
|
|
28
|
+
function opts(file, config, packageFilter2) {
|
|
29
|
+
return Object.assign({
|
|
30
|
+
// more closely matches Node (#333)
|
|
31
|
+
// plus 'mjs' for native modules! (#939)
|
|
32
|
+
extensions: [".mjs", ".js", ".json", ".node"]
|
|
33
|
+
}, config, {
|
|
34
|
+
// path.resolve will handle paths relative to CWD
|
|
35
|
+
basedir: path.dirname(path.resolve(file)),
|
|
36
|
+
packageFilter: packageFilter2
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
function identity(x) {
|
|
40
|
+
return x;
|
|
41
|
+
}
|
|
42
|
+
function packageFilter(pkg, dir, config) {
|
|
43
|
+
let found = false;
|
|
44
|
+
const file = path.join(dir, "dummy.js");
|
|
45
|
+
if (pkg.module) {
|
|
46
|
+
try {
|
|
47
|
+
resolve(String(pkg.module).replace(/^(?:\.\/)?/, "./"), opts(file, config, identity));
|
|
48
|
+
pkg.main = pkg.module;
|
|
49
|
+
found = true;
|
|
50
|
+
} catch (err) {
|
|
51
|
+
log("resolve threw error trying to find pkg.module:", err);
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
if (!found && pkg["jsnext:main"]) {
|
|
55
|
+
try {
|
|
56
|
+
resolve(String(pkg["jsnext:main"]).replace(/^(?:\.\/)?/, "./"), opts(file, config, identity));
|
|
57
|
+
pkg.main = pkg["jsnext:main"];
|
|
58
|
+
found = true;
|
|
59
|
+
} catch (err) {
|
|
60
|
+
log("resolve threw error trying to find pkg['jsnext:main']:", err);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
return pkg;
|
|
64
|
+
}
|
|
@@ -0,0 +1,277 @@
|
|
|
1
|
+
var __create = Object.create;
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __getProtoOf = Object.getPrototypeOf;
|
|
6
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
+
var __export = (target, all) => {
|
|
8
|
+
for (var name in all)
|
|
9
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
10
|
+
};
|
|
11
|
+
var __copyProps = (to, from, except, desc) => {
|
|
12
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
13
|
+
for (let key of __getOwnPropNames(from))
|
|
14
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
15
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
16
|
+
}
|
|
17
|
+
return to;
|
|
18
|
+
};
|
|
19
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
|
20
|
+
// If the importer is in node compatibility mode or this is not an ESM
|
|
21
|
+
// file that has been converted to a CommonJS file using a Babel-
|
|
22
|
+
// compatible transform (i.e. "__esModule" has not been set), then set
|
|
23
|
+
// "default" to the CommonJS "module.exports" for node compatibility.
|
|
24
|
+
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
|
25
|
+
mod
|
|
26
|
+
));
|
|
27
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
28
|
+
|
|
29
|
+
// node_modules/eslint-import-resolver-typescript/lib/index.js
|
|
30
|
+
var lib_exports = {};
|
|
31
|
+
__export(lib_exports, {
|
|
32
|
+
defaultConditionNames: () => defaultConditionNames,
|
|
33
|
+
defaultExtensionAlias: () => defaultExtensionAlias,
|
|
34
|
+
defaultExtensions: () => defaultExtensions,
|
|
35
|
+
defaultMainFields: () => defaultMainFields,
|
|
36
|
+
interfaceVersion: () => interfaceVersion,
|
|
37
|
+
resolve: () => resolve
|
|
38
|
+
});
|
|
39
|
+
module.exports = __toCommonJS(lib_exports);
|
|
40
|
+
var import_node_fs = __toESM(require("node:fs"), 1);
|
|
41
|
+
var import_node_path = __toESM(require("node:path"), 1);
|
|
42
|
+
var import_debug = __toESM(require("debug"), 1);
|
|
43
|
+
var import_enhanced_resolve = __toESM(require("enhanced-resolve"), 1);
|
|
44
|
+
var import_hash = require("eslint-module-utils/hash.js");
|
|
45
|
+
var import_fast_glob = __toESM(require("fast-glob"), 1);
|
|
46
|
+
var import_get_tsconfig = require("get-tsconfig");
|
|
47
|
+
var import_is_core_module = __toESM(require("is-core-module"), 1);
|
|
48
|
+
var import_is_glob = __toESM(require("is-glob"), 1);
|
|
49
|
+
var { globSync } = import_fast_glob.default;
|
|
50
|
+
var IMPORTER_NAME = "eslint-import-resolver-typescript";
|
|
51
|
+
var log = (0, import_debug.default)(IMPORTER_NAME);
|
|
52
|
+
var defaultConditionNames = [
|
|
53
|
+
"types",
|
|
54
|
+
"import",
|
|
55
|
+
"esm2020",
|
|
56
|
+
"es2020",
|
|
57
|
+
"es2015",
|
|
58
|
+
"require",
|
|
59
|
+
"node",
|
|
60
|
+
"node-addons",
|
|
61
|
+
"browser",
|
|
62
|
+
"default"
|
|
63
|
+
];
|
|
64
|
+
var defaultExtensions = [
|
|
65
|
+
".ts",
|
|
66
|
+
".tsx",
|
|
67
|
+
".d.ts",
|
|
68
|
+
".js",
|
|
69
|
+
".jsx",
|
|
70
|
+
".json",
|
|
71
|
+
".node"
|
|
72
|
+
];
|
|
73
|
+
var defaultExtensionAlias = {
|
|
74
|
+
".js": [
|
|
75
|
+
".ts",
|
|
76
|
+
".tsx",
|
|
77
|
+
".d.ts",
|
|
78
|
+
".js"
|
|
79
|
+
],
|
|
80
|
+
".jsx": [".tsx", ".d.ts", ".jsx"],
|
|
81
|
+
".cjs": [".cts", ".d.cts", ".cjs"],
|
|
82
|
+
".mjs": [".mts", ".d.mts", ".mjs"]
|
|
83
|
+
};
|
|
84
|
+
var defaultMainFields = [
|
|
85
|
+
"types",
|
|
86
|
+
"typings",
|
|
87
|
+
"fesm2020",
|
|
88
|
+
"fesm2015",
|
|
89
|
+
"esm2020",
|
|
90
|
+
"es2020",
|
|
91
|
+
"module",
|
|
92
|
+
"jsnext:main",
|
|
93
|
+
"main"
|
|
94
|
+
];
|
|
95
|
+
var interfaceVersion = 2;
|
|
96
|
+
var fileSystem = import_node_fs.default;
|
|
97
|
+
var JS_EXT_PATTERN = /\.(?:[cm]js|jsx?)$/;
|
|
98
|
+
var RELATIVE_PATH_PATTERN = /^\.{1,2}(?:\/.*)?$/;
|
|
99
|
+
var previousOptionsHash;
|
|
100
|
+
var optionsHash;
|
|
101
|
+
var cachedOptions;
|
|
102
|
+
var prevCwd;
|
|
103
|
+
var mappersCachedOptions;
|
|
104
|
+
var mappers;
|
|
105
|
+
var resolverCachedOptions;
|
|
106
|
+
var resolver;
|
|
107
|
+
var digestHashObject = (value) => (0, import_hash.hashObject)(value ?? {}).digest("hex");
|
|
108
|
+
function resolve(source, file, options) {
|
|
109
|
+
if (!cachedOptions || previousOptionsHash !== (optionsHash = digestHashObject(options))) {
|
|
110
|
+
previousOptionsHash = optionsHash;
|
|
111
|
+
cachedOptions = {
|
|
112
|
+
...options,
|
|
113
|
+
conditionNames: options?.conditionNames ?? defaultConditionNames,
|
|
114
|
+
extensions: options?.extensions ?? defaultExtensions,
|
|
115
|
+
extensionAlias: options?.extensionAlias ?? defaultExtensionAlias,
|
|
116
|
+
mainFields: options?.mainFields ?? defaultMainFields,
|
|
117
|
+
fileSystem: new import_enhanced_resolve.default.CachedInputFileSystem(fileSystem, 5 * 1e3),
|
|
118
|
+
useSyncFileSystemCalls: true
|
|
119
|
+
};
|
|
120
|
+
}
|
|
121
|
+
if (!resolver || resolverCachedOptions !== cachedOptions) {
|
|
122
|
+
resolver = import_enhanced_resolve.default.ResolverFactory.createResolver(cachedOptions);
|
|
123
|
+
resolverCachedOptions = cachedOptions;
|
|
124
|
+
}
|
|
125
|
+
log("looking for:", source);
|
|
126
|
+
source = removeQuerystring(source);
|
|
127
|
+
if ((0, import_is_core_module.default)(source)) {
|
|
128
|
+
log("matched core:", source);
|
|
129
|
+
return {
|
|
130
|
+
found: true,
|
|
131
|
+
path: null
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
initMappers(cachedOptions);
|
|
135
|
+
const mappedPath = getMappedPath(source, file, cachedOptions.extensions, true);
|
|
136
|
+
if (mappedPath) {
|
|
137
|
+
log("matched ts path:", mappedPath);
|
|
138
|
+
}
|
|
139
|
+
let foundNodePath;
|
|
140
|
+
try {
|
|
141
|
+
foundNodePath = resolver.resolveSync({}, import_node_path.default.dirname(import_node_path.default.resolve(file)), mappedPath ?? source) || null;
|
|
142
|
+
} catch {
|
|
143
|
+
foundNodePath = null;
|
|
144
|
+
}
|
|
145
|
+
if ((JS_EXT_PATTERN.test(foundNodePath) || cachedOptions.alwaysTryTypes && !foundNodePath) && !/^@types[/\\]/.test(source) && !import_node_path.default.isAbsolute(source) && !source.startsWith(".")) {
|
|
146
|
+
const definitelyTyped = resolve("@types" + import_node_path.default.sep + mangleScopedPackage(source), file, options);
|
|
147
|
+
if (definitelyTyped.found) {
|
|
148
|
+
return definitelyTyped;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
if (foundNodePath) {
|
|
152
|
+
log("matched node path:", foundNodePath);
|
|
153
|
+
return {
|
|
154
|
+
found: true,
|
|
155
|
+
path: foundNodePath
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
log("didn't find ", source);
|
|
159
|
+
return {
|
|
160
|
+
found: false
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
function removeQuerystring(id) {
|
|
164
|
+
const querystringIndex = id.lastIndexOf("?");
|
|
165
|
+
if (querystringIndex >= 0) {
|
|
166
|
+
return id.slice(0, querystringIndex);
|
|
167
|
+
}
|
|
168
|
+
return id;
|
|
169
|
+
}
|
|
170
|
+
var isFile = (path2) => {
|
|
171
|
+
try {
|
|
172
|
+
return !!(path2 && import_node_fs.default.statSync(path2, { throwIfNoEntry: false })?.isFile());
|
|
173
|
+
} catch {
|
|
174
|
+
return false;
|
|
175
|
+
}
|
|
176
|
+
};
|
|
177
|
+
var isModule = (modulePath) => {
|
|
178
|
+
return !!modulePath && isFile(import_node_path.default.resolve(modulePath, "package.json"));
|
|
179
|
+
};
|
|
180
|
+
function getMappedPath(source, file, extensions = defaultExtensions, retry) {
|
|
181
|
+
const originalExtensions = extensions;
|
|
182
|
+
extensions = ["", ...extensions];
|
|
183
|
+
let paths = [];
|
|
184
|
+
if (RELATIVE_PATH_PATTERN.test(source)) {
|
|
185
|
+
const resolved = import_node_path.default.resolve(import_node_path.default.dirname(file), source);
|
|
186
|
+
if (isFile(resolved)) {
|
|
187
|
+
paths = [resolved];
|
|
188
|
+
}
|
|
189
|
+
} else {
|
|
190
|
+
paths = mappers.map((mapper) => mapper?.(source).map((item) => [
|
|
191
|
+
...extensions.map((ext) => `${item}${ext}`),
|
|
192
|
+
...originalExtensions.map((ext) => `${item}/index${ext}`)
|
|
193
|
+
])).flat(2).filter((mappedPath) => {
|
|
194
|
+
if (mappedPath === void 0) {
|
|
195
|
+
return false;
|
|
196
|
+
}
|
|
197
|
+
try {
|
|
198
|
+
const stat = import_node_fs.default.statSync(mappedPath, { throwIfNoEntry: false });
|
|
199
|
+
if (stat === void 0)
|
|
200
|
+
return false;
|
|
201
|
+
if (stat.isFile())
|
|
202
|
+
return true;
|
|
203
|
+
if (stat.isDirectory()) {
|
|
204
|
+
return isModule(mappedPath);
|
|
205
|
+
}
|
|
206
|
+
} catch {
|
|
207
|
+
return false;
|
|
208
|
+
}
|
|
209
|
+
return false;
|
|
210
|
+
});
|
|
211
|
+
}
|
|
212
|
+
if (retry && paths.length === 0) {
|
|
213
|
+
const isJs = JS_EXT_PATTERN.test(source);
|
|
214
|
+
if (isJs) {
|
|
215
|
+
const jsExt = import_node_path.default.extname(source);
|
|
216
|
+
const tsExt = jsExt.replace("js", "ts");
|
|
217
|
+
const basename = source.replace(JS_EXT_PATTERN, "");
|
|
218
|
+
const resolved = getMappedPath(basename + tsExt, file) || getMappedPath(basename + ".d" + (tsExt === ".tsx" ? ".ts" : tsExt), file);
|
|
219
|
+
if (resolved) {
|
|
220
|
+
return resolved;
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
for (const ext of extensions) {
|
|
224
|
+
const resolved = (isJs ? null : getMappedPath(source + ext, file)) || getMappedPath(source + `/index${ext}`, file);
|
|
225
|
+
if (resolved) {
|
|
226
|
+
return resolved;
|
|
227
|
+
}
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
if (paths.length > 1) {
|
|
231
|
+
log("found multiple matching ts paths:", paths);
|
|
232
|
+
}
|
|
233
|
+
return paths[0];
|
|
234
|
+
}
|
|
235
|
+
function initMappers(options) {
|
|
236
|
+
if (mappers && mappersCachedOptions === options && prevCwd === process.cwd()) {
|
|
237
|
+
return;
|
|
238
|
+
}
|
|
239
|
+
prevCwd = process.cwd();
|
|
240
|
+
const configPaths = typeof options.project === "string" ? [options.project] : Array.isArray(options.project) ? options.project : [process.cwd()];
|
|
241
|
+
const ignore = ["!**/node_modules/**"];
|
|
242
|
+
const projectPaths = [
|
|
243
|
+
.../* @__PURE__ */ new Set([
|
|
244
|
+
...configPaths.filter((path2) => !(0, import_is_glob.default)(path2)),
|
|
245
|
+
...globSync([...configPaths.filter((path2) => (0, import_is_glob.default)(path2)), ...ignore])
|
|
246
|
+
])
|
|
247
|
+
];
|
|
248
|
+
mappers = projectPaths.map((projectPath) => {
|
|
249
|
+
let tsconfigResult;
|
|
250
|
+
if (isFile(projectPath)) {
|
|
251
|
+
const { dir, base } = import_node_path.default.parse(projectPath);
|
|
252
|
+
tsconfigResult = (0, import_get_tsconfig.getTsconfig)(dir, base);
|
|
253
|
+
} else {
|
|
254
|
+
tsconfigResult = (0, import_get_tsconfig.getTsconfig)(projectPath);
|
|
255
|
+
}
|
|
256
|
+
return tsconfigResult && (0, import_get_tsconfig.createPathsMatcher)(tsconfigResult);
|
|
257
|
+
});
|
|
258
|
+
mappersCachedOptions = options;
|
|
259
|
+
}
|
|
260
|
+
function mangleScopedPackage(moduleName) {
|
|
261
|
+
if (moduleName.startsWith("@")) {
|
|
262
|
+
const replaceSlash = moduleName.replace(import_node_path.default.sep, "__");
|
|
263
|
+
if (replaceSlash !== moduleName) {
|
|
264
|
+
return replaceSlash.slice(1);
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
return moduleName;
|
|
268
|
+
}
|
|
269
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
270
|
+
0 && (module.exports = {
|
|
271
|
+
defaultConditionNames,
|
|
272
|
+
defaultExtensionAlias,
|
|
273
|
+
defaultExtensions,
|
|
274
|
+
defaultMainFields,
|
|
275
|
+
interfaceVersion,
|
|
276
|
+
resolve
|
|
277
|
+
});
|