Skip to content

Commit 1fc0bf6

Browse files
Toilalaladdin-add
andauthored
feat: no-unpublished-import supports ignoreTypeImport (fixes #78) (#79)
* fix: skip import type nodes in no-unpublished-import rule (#78) * feat: no-unpublished-import supports ignoreTypeImport --------- Co-authored-by: 唯然 <weiran.zsd@outlook.com>
1 parent e43d4ea commit 1fc0bf6

File tree

7 files changed

+78
-5
lines changed

7 files changed

+78
-5
lines changed

docs/rules/no-unpublished-import.md

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,26 @@ In addition, we can specify glob patterns to exclude files.
108108

109109
TODO
110110

111+
### ignoreTypeImport
112+
113+
If using typescript, you may want to ignore type imports. This option allows you to do that.
114+
115+
```json
116+
{
117+
"rules": {
118+
"n/no-unpublished-import": ["error", {
119+
"ignoreTypeImport": true
120+
}]
121+
}
122+
}
123+
```
124+
125+
In this way, the following code will not be reported:
126+
127+
```ts
128+
import type foo from "foo";
129+
```
130+
111131
### Shared Settings
112132

113133
The following options can be set by [shared settings](http://eslint.org/docs/user-guide/configuring.html#adding-shared-settings).

lib/rules/no-unpublished-import.js

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ module.exports = {
2828
allowModules: getAllowModules.schema,
2929
convertPath: getConvertPath.schema,
3030
resolvePaths: getResolvePaths.schema,
31+
ignoreTypeImport: { type: "boolean", default: false },
3132
},
3233
additionalProperties: false,
3334
},
@@ -36,11 +37,17 @@ module.exports = {
3637
},
3738
create(context) {
3839
const filePath = context.getFilename()
40+
const options = context.options[0] || {}
41+
const ignoreTypeImport =
42+
options.ignoreTypeImport === void 0
43+
? false
44+
: options.ignoreTypeImport
45+
3946
if (filePath === "<input>") {
4047
return {}
4148
}
4249

43-
return visitImport(context, {}, targets => {
50+
return visitImport(context, { ignoreTypeImport }, targets => {
4451
checkPublish(context, filePath, targets)
4552
})
4653
},

lib/util/check-publish.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ exports.checkPublish = function checkPublish(context, filePath, targets) {
7474
context.report({
7575
node: target.node,
7676
loc: target.node.loc,
77-
message: '"{{name}}" is not published.',
77+
messageId: "notPublished",
7878
data: { name: target.moduleName || target.name },
7979
})
8080
}

lib/util/visit-import.js

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,12 +20,13 @@ const stripImportPathParams = require("./strip-import-path-params")
2020
* @param {Object} [options] - The flag to include core modules.
2121
* @param {boolean} [options.includeCore] - The flag to include core modules.
2222
* @param {number} [options.optionIndex] - The index of rule options.
23+
* @param {boolean} [options.ignoreTypeImport] - The flag to ignore typescript type imports.
2324
* @param {function(ImportTarget[]):void} callback The callback function to get result.
2425
* @returns {ImportTarget[]} A list of found target's information.
2526
*/
2627
module.exports = function visitImport(
2728
context,
28-
{ includeCore = false, optionIndex = 0 } = {},
29+
{ includeCore = false, optionIndex = 0, ignoreTypeImport = false } = {},
2930
callback
3031
) {
3132
const targets = []
@@ -52,6 +53,15 @@ module.exports = function visitImport(
5253
return
5354
}
5455

56+
// skip `import type { foo } from 'bar'` (for eslint-typescript)
57+
if (
58+
ignoreTypeImport &&
59+
node.type === "ImportDeclaration" &&
60+
node.importKind === "type"
61+
) {
62+
return
63+
}
64+
5565
const name = sourceNode && stripImportPathParams(sourceNode.value)
5666
// Note: "999" arbitrary to check current/future Node.js version
5767
if (name && (includeCore || !isCoreModule(name, "999"))) {

package.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
"semver": "^7.3.8"
2424
},
2525
"devDependencies": {
26+
"@typescript-eslint/parser": "^5.51.0",
2627
"codecov": "^3.3.0",
2728
"esbuild": "^0.14.39",
2829
"eslint": "^8.27.0",
@@ -43,7 +44,8 @@
4344
"prettier": "^2.7.1",
4445
"punycode": "^2.1.1",
4546
"release-it": "^15.5.0",
46-
"rimraf": "^3.0.2"
47+
"rimraf": "^3.0.2",
48+
"typescript": "^4.9.5"
4749
},
4850
"scripts": {
4951
"build": "node scripts/update",

tests/fixtures/no-unpublished/1/package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
"aaa": "0.0.0"
66
},
77
"devDependencies": {
8-
"bbb": "0.0.0"
8+
"bbb": "0.0.0",
9+
"foo": "0.0.0"
910
}
1011
}

tests/lib/rules/no-unpublished-import.js

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -151,6 +151,17 @@ ruleTester.run("no-unpublished-import", rule, {
151151
filename: fixture("private-package/index.js"),
152152
code: "import bbb from 'bbb';",
153153
},
154+
155+
// https://github.com/eslint-community/eslint-plugin-n/issues/78
156+
{
157+
filename: fixture("1/test.ts"),
158+
parser: path.join(
159+
__dirname,
160+
"../../../node_modules/@typescript-eslint/parser"
161+
),
162+
code: "import type foo from 'foo';",
163+
options: [{ ignoreTypeImport: true }],
164+
},
154165
],
155166
invalid: [
156167
{
@@ -272,5 +283,27 @@ ruleTester.run("no-unpublished-import", rule, {
272283
},
273284
]
274285
: []),
286+
287+
// https://github.com/eslint-community/eslint-plugin-n/issues/78
288+
{
289+
filename: fixture("1/test.ts"),
290+
parser: path.join(
291+
__dirname,
292+
"../../../node_modules/@typescript-eslint/parser"
293+
),
294+
code: "import type foo from 'foo';",
295+
options: [{ ignoreTypeImport: false }],
296+
errors: [{ messageId: "notPublished" }],
297+
},
298+
299+
{
300+
filename: fixture("1/test.ts"),
301+
parser: path.join(
302+
__dirname,
303+
"../../../node_modules/@typescript-eslint/parser"
304+
),
305+
code: "import type foo from 'foo';",
306+
errors: [{ messageId: "notPublished" }],
307+
},
275308
],
276309
})

0 commit comments

Comments
 (0)