diff --git a/packages/eslint-plugin/src/rules/no-restricted-imports.ts b/packages/eslint-plugin/src/rules/no-restricted-imports.ts index e8550856c2c2..d22f9b5d058f 100644 --- a/packages/eslint-plugin/src/rules/no-restricted-imports.ts +++ b/packages/eslint-plugin/src/rules/no-restricted-imports.ts @@ -267,24 +267,38 @@ export default createRule({ const restrictedPatterns = getRestrictedPatterns(options); const allowedImportTypeMatchers: Ignore[] = []; + const allowedImportTypeRegexMatchers: RegExp[] = []; for (const restrictedPattern of restrictedPatterns) { if ( typeof restrictedPattern === 'object' && restrictedPattern.allowTypeImports ) { // Following how ignore is configured in the base rule - allowedImportTypeMatchers.push( - ignore({ - allowRelativePaths: true, - ignoreCase: !restrictedPattern.caseSensitive, - }).add(restrictedPattern.group), - ); + if (restrictedPattern.group) { + allowedImportTypeMatchers.push( + ignore({ + allowRelativePaths: true, + ignoreCase: !restrictedPattern.caseSensitive, + }).add(restrictedPattern.group), + ); + } + if (restrictedPattern.regex) { + allowedImportTypeRegexMatchers.push( + new RegExp( + restrictedPattern.regex, + restrictedPattern.caseSensitive ? 'u' : 'iu', + ), + ); + } } } function isAllowedTypeImportPattern(importSource: string): boolean { return ( // As long as there's one matching pattern that allows type import - allowedImportTypeMatchers.some(matcher => matcher.ignores(importSource)) + allowedImportTypeMatchers.some(matcher => + matcher.ignores(importSource), + ) || + allowedImportTypeRegexMatchers.some(regex => regex.test(importSource)) ); } diff --git a/packages/eslint-plugin/tests/rules/no-restricted-imports.test.ts b/packages/eslint-plugin/tests/rules/no-restricted-imports.test.ts index 5640f285264f..b43a52ef8d71 100644 --- a/packages/eslint-plugin/tests/rules/no-restricted-imports.test.ts +++ b/packages/eslint-plugin/tests/rules/no-restricted-imports.test.ts @@ -290,6 +290,43 @@ import type { foo } from 'import2/private/bar'; }, ], }, + { + code: ` +import type { foo } from 'import1/private/bar'; +import type { foo } from 'import2/private/bar'; + `, + options: [ + { + patterns: [ + { + allowTypeImports: true, + message: 'usage of import1 private modules not allowed.', + regex: 'import1/.*', + }, + { + allowTypeImports: true, + message: 'usage of import2 private modules not allowed.', + regex: 'import2/.*', + }, + ], + }, + ], + }, + { + code: "import { foo } from 'import1/private';", + options: [ + { + patterns: [ + { + allowTypeImports: true, + caseSensitive: true, + message: 'usage of import1 private modules not allowed.', + regex: 'import1/[A-Z]+', + }, + ], + }, + ], + }, { code: "import { type Bar } from 'import-foo';", options: [ @@ -722,6 +759,47 @@ import type { foo } from 'import2/private/bar'; }, ], }, + { + code: "export { foo } from 'import1/private/bar';", + errors: [ + { + messageId: 'patternWithCustomMessage', + type: AST_NODE_TYPES.ExportNamedDeclaration, + }, + ], + options: [ + { + patterns: [ + { + allowTypeImports: true, + message: 'usage of import1 private modules not allowed.', + regex: 'import1/.*', + }, + ], + }, + ], + }, + { + code: "import { foo } from 'import1/private-package';", + errors: [ + { + messageId: 'patternWithCustomMessage', + type: AST_NODE_TYPES.ImportDeclaration, + }, + ], + options: [ + { + patterns: [ + { + allowTypeImports: true, + caseSensitive: true, + message: 'usage of import1 private modules not allowed.', + regex: 'import1/private-[a-z]*', + }, + ], + }, + ], + }, { code: "export * from 'import1';", errors: [ diff --git a/packages/eslint-plugin/typings/eslint-rules.d.ts b/packages/eslint-plugin/typings/eslint-rules.d.ts index 6632125e3b15..970839e19c01 100644 --- a/packages/eslint-plugin/typings/eslint-rules.d.ts +++ b/packages/eslint-plugin/typings/eslint-rules.d.ts @@ -558,7 +558,8 @@ declare module 'eslint/lib/rules/no-restricted-imports' { // extended allowTypeImports?: boolean; caseSensitive?: boolean; - group: string[]; + group?: string[]; + regex?: string; message?: string; }[] | string[]; pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy