Skip to content

Commit

Permalink
[New] no-namespace: Add ignore option
Browse files Browse the repository at this point in the history
Closes #1916.
Closes #1903.
  • Loading branch information
Arkadii Berezkin authored and ljharb committed Jun 2, 2021
1 parent 54d86c8 commit bba59c4
Show file tree
Hide file tree
Showing 4 changed files with 39 additions and 7 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Expand Up @@ -9,6 +9,7 @@ This change log adheres to standards from [Keep a CHANGELOG](http://keepachangel
### Added
- [`no-dynamic-require`]: add option `esmodule` ([#1223], thanks [@vikr01])
- [`named`]: add `commonjs` option ([#1222], thanks [@vikr01])
- [`no-namespace`]: Add `ignore` option ([#2112], thanks [@aberezkin])

### Fixed
- [`no-duplicates`]: ensure autofix avoids excessive newlines ([#2028], thanks [@ertrzyiks])
Expand Down Expand Up @@ -822,6 +823,7 @@ for info on changes for earlier releases.
[#2146]: https://github.com/benmosher/eslint-plugin-import/pull/2146
[#2138]: https://github.com/benmosher/eslint-plugin-import/pull/2138
[#2121]: https://github.com/benmosher/eslint-plugin-import/pull/2121
[#2112]: https://github.com/benmosher/eslint-plugin-import/pull/2112
[#2099]: https://github.com/benmosher/eslint-plugin-import/pull/2099
[#2097]: https://github.com/benmosher/eslint-plugin-import/pull/2097
[#2090]: https://github.com/benmosher/eslint-plugin-import/pull/2090
Expand Down Expand Up @@ -1252,6 +1254,7 @@ for info on changes for earlier releases.
[@1pete]: https://github.com/1pete
[@3nuc]: https://github.com/3nuc
[@aamulumi]: https://github.com/aamulumi
[@aberezkin]: https://github.com/aberezkin
[@adamborowski]: https://github.com/adamborowski
[@adjerbetian]: https://github.com/adjerbetian
[@ai]: https://github.com/ai
Expand Down
11 changes: 11 additions & 0 deletions docs/rules/no-namespace.md
Expand Up @@ -5,6 +5,12 @@ Enforce a convention of not using namespace (a.k.a. "wildcard" `*`) imports.
+(fixable) The `--fix` option on the [command line] automatically fixes problems reported by this rule, provided that the namespace object is only used for direct member access, e.g. `namespace.a`.
The `--fix` functionality for this rule requires ESLint 5 or newer.

### Options

This rule supports the following options:

- `ignore`: array of glob strings for modules that should be ignored by the rule.

## Rule Details

Valid:
Expand All @@ -15,6 +21,11 @@ import { a, b } from './bar'
import defaultExport, { a, b } from './foobar'
```

```js
/* eslint import/no-namespace: ["error", {ignore: ['*.ext']] */

This comment has been minimized.

Copy link
@gairon

gairon Sep 21, 2021

Looks like there missed } at the end of the option.

import * as bar from './ignored-module.ext';
```

Invalid:

```js
Expand Down
31 changes: 24 additions & 7 deletions src/rules/no-namespace.js
Expand Up @@ -3,6 +3,7 @@
* @author Radek Benkel
*/

import minimatch from 'minimatch';
import docsUrl from '../docsUrl';

//------------------------------------------------------------------------------
Expand All @@ -17,16 +18,32 @@ module.exports = {
url: docsUrl('no-namespace'),
},
fixable: 'code',
schema: [],
schema: [{
type: 'object',
properties: {
ignore: {
type: 'array',
items: {
type: 'string',
},
uniqueItems: true,
},
},
}],
},

create: function (context) {
const firstOption = context.options[0] || {};
const ignoreGlobs = firstOption.ignore;

return {
'ImportNamespaceSpecifier': function (node) {
ImportNamespaceSpecifier(node) {
if (ignoreGlobs && ignoreGlobs.find(glob => minimatch(node.parent.source.value, glob, { matchBase: true }))) {
return;
}

const scopeVariables = context.getScope().variables;
const namespaceVariable = scopeVariables.find((variable) =>
variable.defs[0].node === node
);
const namespaceVariable = scopeVariables.find((variable) => variable.defs[0].node === node);
const namespaceReferences = namespaceVariable.references;
const namespaceIdentifiers = namespaceReferences.map(reference => reference.identifier);
const canFix = namespaceIdentifiers.length > 0 && !usesNamespaceAsObject(namespaceIdentifiers);
Expand Down Expand Up @@ -63,11 +80,11 @@ module.exports = {
);

// Replace the ImportNamespaceSpecifier with a list of ImportSpecifiers
const namedImportSpecifiers = importNames.map((importName) =>
const namedImportSpecifiers = importNames.map((importName) => (
importName === importLocalNames[importName]
? importName
: `${importName} as ${importLocalNames[importName]}`
);
));
fixes.push(fixer.replaceText(node, `{ ${namedImportSpecifiers.join(', ')} }`));

// Pass 2: Replace references to the namespace with references to the named imports
Expand Down
1 change: 1 addition & 0 deletions tests/src/rules/no-namespace.js
Expand Up @@ -78,6 +78,7 @@ ruleTester.run('no-namespace', require('rules/no-namespace'), {
{ code: 'import { a, b } from \'./foo\';', parserOptions: { ecmaVersion: 2015, sourceType: 'module' } },
{ code: 'import bar from \'bar\';', parserOptions: { ecmaVersion: 2015, sourceType: 'module' } },
{ code: 'import bar from \'./bar\';', parserOptions: { ecmaVersion: 2015, sourceType: 'module' } },
{ code: 'import * as bar from \'./ignored-module.ext\';', parserOptions: { ecmaVersion: 2015, sourceType: 'module' }, options: [{ ignore: ['*.ext'] }] },
],

invalid: [
Expand Down

0 comments on commit bba59c4

Please sign in to comment.