@definitelytyped/eslint-plugin 0.0.179 → 0.0.181

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.
Files changed (49) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/dist/rules/index.d.ts +5 -4
  3. package/dist/rules/index.js +6 -4
  4. package/dist/rules/index.js.map +1 -1
  5. package/dist/rules/no-bad-reference.d.ts +1 -1
  6. package/dist/rules/no-bad-reference.js +7 -9
  7. package/dist/rules/no-bad-reference.js.map +1 -1
  8. package/dist/rules/no-import-of-dev-dependencies.d.ts +2 -0
  9. package/dist/rules/no-import-of-dev-dependencies.js +89 -0
  10. package/dist/rules/no-import-of-dev-dependencies.js.map +1 -0
  11. package/dist/rules/no-old-dt-header.d.ts +2 -0
  12. package/dist/rules/no-old-dt-header.js +37 -0
  13. package/dist/rules/no-old-dt-header.js.map +1 -0
  14. package/dist/rules/no-self-import.d.ts +1 -1
  15. package/dist/rules/no-self-import.js +8 -1
  16. package/dist/rules/no-self-import.js.map +1 -1
  17. package/dist/rules/no-single-declare-module.d.ts +2 -0
  18. package/dist/rules/no-single-declare-module.js +75 -0
  19. package/dist/rules/no-single-declare-module.js.map +1 -0
  20. package/dist/rules/no-useless-files.js +2 -8
  21. package/dist/rules/no-useless-files.js.map +1 -1
  22. package/dist/util.d.ts +3 -1
  23. package/dist/util.js +9 -1
  24. package/dist/util.js.map +1 -1
  25. package/package.json +3 -3
  26. package/src/rules/index.ts +6 -4
  27. package/src/rules/no-bad-reference.ts +9 -13
  28. package/src/rules/no-import-of-dev-dependencies.ts +84 -0
  29. package/src/rules/no-old-dt-header.ts +40 -0
  30. package/src/rules/no-self-import.ts +8 -2
  31. package/src/rules/no-single-declare-module.ts +58 -0
  32. package/src/rules/no-useless-files.ts +3 -9
  33. package/src/util.ts +13 -2
  34. package/test/no-bad-reference.test.ts +68 -0
  35. package/test/no-import-of-dev-dependencies.test.ts +72 -0
  36. package/test/no-old-dt-header.test.ts +71 -0
  37. package/test/no-self-import.test.ts +68 -0
  38. package/test/no-single-declare-module.test.ts +50 -0
  39. package/test/tsconfig.no-single-declare-module.json +7 -0
  40. package/tsconfig.tsbuildinfo +1 -1
  41. package/dist/rules/dt-header.d.ts +0 -2
  42. package/dist/rules/dt-header.js +0 -62
  43. package/dist/rules/dt-header.js.map +0 -1
  44. package/dist/rules/no-outside-dependencies.d.ts +0 -2
  45. package/dist/rules/no-outside-dependencies.js +0 -41
  46. package/dist/rules/no-outside-dependencies.js.map +0 -1
  47. package/src/rules/dt-header.ts +0 -74
  48. package/src/rules/no-outside-dependencies.ts +0 -42
  49. package/test/dt-header.test.ts +0 -189
@@ -1,15 +1,14 @@
1
1
  import { TSESTree } from "@typescript-eslint/utils";
2
- import { createRule } from "../util";
3
-
4
- type MessageId = "referencePathPackage" | "referencePathTest";
2
+ import { commentsMatching, createRule } from "../util";
5
3
 
4
+ type MessageId = "referencePathPackage" | "referencePathTest" | "referencePathOldVersion";
6
5
  const rule = createRule({
7
6
  name: "no-bad-reference",
8
7
  defaultOptions: [],
9
8
  meta: {
10
9
  type: "problem",
11
10
  docs: {
12
- description: `Forbids <reference path="../etc"/> in any file, and forbid <reference path> in test files.`,
11
+ description: `Forbids <reference path="./vNN"/> in all files, <reference path="../etc"/> in declaration files, and all <reference path> in test files.`,
13
12
  recommended: "error",
14
13
  },
15
14
  messages: {
@@ -17,27 +16,24 @@ const rule = createRule({
17
16
  "Don't use <reference path> to reference another package. Use an import or <reference types> instead.",
18
17
  referencePathTest:
19
18
  "Don't use <reference path> in test files. Use <reference types> or include the file in 'tsconfig.json'.",
19
+ referencePathOldVersion: "Don't use <reference path> to reference an old version of the current package.",
20
20
  },
21
21
  schema: [],
22
22
  },
23
23
  create(context) {
24
- const { comments } = context.getSourceCode().ast;
25
24
  const isDeclarationFile = context.getFilename().endsWith(".d.ts");
26
-
27
- for (const comment of comments) {
28
- const referenceMatch = comment.value.match(/<reference\s+path\s*=\s*"(.+)"\s*\/>/)?.[1];
29
- if (!referenceMatch) {
30
- continue;
25
+ commentsMatching(context.getSourceCode(), /<reference\s+path\s*=\s*"(.+)"\s*\/>/, (ref, comment) => {
26
+ if (ref.match(/^\.\/v\d+(?:\.\d+)?(?:\/.*)?$/)) {
27
+ report(comment, "referencePathOldVersion");
31
28
  }
32
-
33
29
  if (isDeclarationFile) {
34
- if (referenceMatch.startsWith("..")) {
30
+ if (ref.startsWith("..")) {
35
31
  report(comment, "referencePathPackage");
36
32
  }
37
33
  } else {
38
34
  report(comment, "referencePathTest");
39
35
  }
40
- }
36
+ });
41
37
 
42
38
  return {};
43
39
 
@@ -0,0 +1,84 @@
1
+ import { TSESTree } from "@typescript-eslint/utils";
2
+ import { createRule, commentsMatching, getTypesPackageForDeclarationFile } from "../util";
3
+ import fs from "fs";
4
+ import path from "path";
5
+
6
+ type MessageId = "noImportOfDevDependencies" | "noReferenceOfDevDependencies";
7
+ const rule = createRule({
8
+ name: "no-import-of-dev-dependencies",
9
+ defaultOptions: [],
10
+ meta: {
11
+ type: "problem",
12
+ docs: {
13
+ description: "Forbid imports and references to devDependencies inside .d.ts files.",
14
+ recommended: "error",
15
+ },
16
+ messages: {
17
+ noImportOfDevDependencies: `.d.ts files may not import packages in devDependencies.`,
18
+ noReferenceOfDevDependencies: `.d.ts files may not triple-slash reference packages in devDependencies.`,
19
+ },
20
+ schema: [],
21
+ },
22
+ create(context) {
23
+ const packageName = getTypesPackageForDeclarationFile(context.getFilename());
24
+ if (context.getFilename().endsWith(".d.ts")) {
25
+ const packageJson = getPackageJson(context.getPhysicalFilename?.() ?? context.getFilename());
26
+ const devdeps = packageJson
27
+ ? Object.keys(packageJson.devDependencies).map((dep) => dep.replace(/@types\//, ""))
28
+ : [];
29
+ commentsMatching(context.getSourceCode(), /<reference\s+types\s*=\s*"(.+)"\s*\/>/, (ref, comment) => {
30
+ if (devdeps.includes(ref) && ref !== packageName) {
31
+ report(comment, "noReferenceOfDevDependencies");
32
+ }
33
+ });
34
+
35
+ return {
36
+ // eslint-disable-next-line @typescript-eslint/naming-convention
37
+ ImportDeclaration(node) {
38
+ if (devdeps.includes(node.source.value) && node.source.value !== packageName) {
39
+ context.report({
40
+ messageId: "noImportOfDevDependencies",
41
+ node,
42
+ });
43
+ }
44
+ },
45
+ };
46
+ } else {
47
+ return {};
48
+ }
49
+ function report(comment: TSESTree.Comment, messageId: MessageId) {
50
+ context.report({
51
+ loc: {
52
+ end: {
53
+ column: comment.value.lastIndexOf(`"`),
54
+ line: comment.loc.end.line,
55
+ },
56
+ start: {
57
+ column: comment.value.indexOf(`"`) + 1,
58
+ line: comment.loc.start.line,
59
+ },
60
+ },
61
+ messageId,
62
+ });
63
+ }
64
+ },
65
+ });
66
+ function getPackageJson(sourceFile: string): { devDependencies: Record<string, string> } | undefined {
67
+ let dir = path.dirname(sourceFile);
68
+ let text: string | undefined;
69
+ while (dir !== "/") {
70
+ try {
71
+ text = fs.readFileSync(path.join(dir, "package.json"), "utf8");
72
+ break;
73
+ } catch {
74
+ // presumably because file does not exist, so continue
75
+ }
76
+ dir = path.dirname(dir);
77
+ }
78
+ if (!text) return undefined;
79
+ const json = JSON.parse(text);
80
+ if ("devDependencies" in json) return json;
81
+ return undefined;
82
+ }
83
+
84
+ export = rule;
@@ -0,0 +1,40 @@
1
+ import { createRule } from "../util";
2
+
3
+ const rule = createRule({
4
+ name: "no-bad-reference",
5
+ defaultOptions: [],
6
+ meta: {
7
+ type: "problem",
8
+ docs: {
9
+ description: `Forbids <reference path="./vNN"/> in all files, <reference path="../etc"/> in declaration files, and all <reference path> in test files.`,
10
+ recommended: "error",
11
+ },
12
+ messages: {
13
+ noOldDTHeader:
14
+ "Specify package metadata in package.json. Do not use a header like `// Type definitions for foo 1.2`",
15
+ },
16
+ schema: [],
17
+ },
18
+ create(context) {
19
+ const text = context.getSourceCode().text;
20
+ if (
21
+ context.getFilename().endsWith(".d.ts") &&
22
+ text.indexOf("// Type definitions for ") === 0 &&
23
+ text.indexOf("// Definitions by: ") > 0
24
+ ) {
25
+ context.report({
26
+ messageId: "noOldDTHeader",
27
+ loc: {
28
+ start: { column: 0, line: 1 },
29
+ end: {
30
+ column: "// Type definitions for ".length,
31
+ line: 1,
32
+ },
33
+ },
34
+ });
35
+ }
36
+ return {};
37
+ },
38
+ });
39
+
40
+ export = rule;
@@ -1,16 +1,17 @@
1
1
  import { createRule, getTypesPackageForDeclarationFile } from "../util";
2
-
3
2
  const rule = createRule({
4
3
  name: "no-self-import",
5
4
  defaultOptions: [],
6
5
  meta: {
7
6
  type: "problem",
8
7
  docs: {
9
- description: "Forbids declaration files to import the current package using a global import.",
8
+ description:
9
+ "Forbids declaration files to import the current package using a global import or old versions with a relative import.",
10
10
  recommended: "error",
11
11
  },
12
12
  messages: {
13
13
  useRelativeImport: "Declaration file should not use a global import of itself. Use a relative import.",
14
+ useOnlyCurrentVersion: "Don't import an old version of the current package.",
14
15
  },
15
16
  schema: [],
16
17
  },
@@ -25,6 +26,11 @@ const rule = createRule({
25
26
  messageId: "useRelativeImport",
26
27
  node,
27
28
  });
29
+ } else if (node.source.value.match(/^\.\/v\d+(?:\.\d+)?(?:\/.*)?$/)) {
30
+ context.report({
31
+ messageId: "useOnlyCurrentVersion",
32
+ node,
33
+ });
28
34
  }
29
35
  },
30
36
  };
@@ -0,0 +1,58 @@
1
+ import { ESLintUtils } from "@typescript-eslint/utils";
2
+ import * as ts from "typescript";
3
+
4
+ import { createRule } from "../util";
5
+
6
+ const rule = createRule({
7
+ defaultOptions: [],
8
+ meta: {
9
+ docs: {
10
+ description: "Don't use an ambient module declaration if there's just one -- write it as a normal module.",
11
+ recommended: "error",
12
+ },
13
+ messages: {
14
+ oneModuleDeclaration:
15
+ "File has only 1 ambient module declaration. Move the contents outside the ambient module block, rename the file to match the ambient module name, and remove the block.",
16
+ },
17
+ schema: [],
18
+ type: "problem",
19
+ },
20
+ name: "no-single-declare-module",
21
+ create(context) {
22
+ const services = ESLintUtils.getParserServices(context);
23
+ const sourceFile = services.esTreeNodeToTSNodeMap.get(context.getSourceCode().ast);
24
+
25
+ // If it's an external module, any module declarations inside are augmentations.
26
+ if (ts.isExternalModule(sourceFile)) {
27
+ return {};
28
+ }
29
+
30
+ let moduleDeclaration: ts.ModuleDeclaration | undefined;
31
+ for (const statement of sourceFile.statements) {
32
+ if (ts.isModuleDeclaration(statement) && ts.isStringLiteral(statement.name)) {
33
+ if (statement.name.text.indexOf("*") !== -1) {
34
+ // Ignore wildcard module declarations
35
+ return {};
36
+ }
37
+
38
+ if (moduleDeclaration === undefined) {
39
+ moduleDeclaration = statement;
40
+ } else {
41
+ // Has more than 1 declaration
42
+ return {};
43
+ }
44
+ }
45
+ }
46
+
47
+ if (moduleDeclaration) {
48
+ context.report({
49
+ messageId: "oneModuleDeclaration",
50
+ node: services.tsNodeToESTreeNodeMap.get(moduleDeclaration),
51
+ });
52
+ }
53
+
54
+ return {};
55
+ },
56
+ });
57
+
58
+ export = rule;
@@ -1,4 +1,4 @@
1
- import { createRule } from "../util";
1
+ import { commentsMatching, createRule } from "../util";
2
2
 
3
3
  const rule = createRule({
4
4
  name: "no-useless-files",
@@ -25,15 +25,9 @@ const rule = createRule({
25
25
  } else {
26
26
  const referenceRegExp = /^\/\s*<reference\s*(types|path)\s*=\s*["|'](.*)["|']/;
27
27
  let noReferenceFound = true;
28
-
29
- for (const comment of comments) {
30
- const referenceMatch = comment.value.match(referenceRegExp)?.[1];
31
- if (!referenceMatch) {
32
- continue;
33
- }
28
+ commentsMatching(context.getSourceCode(), referenceRegExp, () => {
34
29
  noReferenceFound = false;
35
- break;
36
- }
30
+ });
37
31
 
38
32
  if (noReferenceFound) {
39
33
  reportNoContent();
package/src/util.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { unmangleScopedPackage } from "@definitelytyped/utils";
2
- import { ESLintUtils } from "@typescript-eslint/utils";
2
+ import { TSESTree, ESLintUtils } from "@typescript-eslint/utils";
3
3
  import { RuleWithMetaAndName } from "@typescript-eslint/utils/dist/eslint-utils";
4
- import { RuleListener, RuleModule } from "@typescript-eslint/utils/dist/ts-eslint";
4
+ import { RuleListener, RuleModule, SourceCode } from "@typescript-eslint/utils/dist/ts-eslint";
5
5
  import { basename, dirname } from "path";
6
6
 
7
7
  // Possible TS bug can't figure out how to do declaration emit of created rules
@@ -46,3 +46,14 @@ export function isMainFile(fileName: string, allowNested: boolean) {
46
46
  // Allow "types/foo/index.d.ts", not "types/foo/utils/index.d.ts"
47
47
  return basename(dirname(parent)) === "types";
48
48
  }
49
+
50
+ export function commentsMatching(
51
+ sourceFile: Readonly<SourceCode>,
52
+ regex: RegExp,
53
+ f: (match: string, c: TSESTree.Comment) => void
54
+ ): void {
55
+ for (const comment of sourceFile.ast.comments) {
56
+ const m = comment.value.match(regex);
57
+ if (m) f(m[1], comment);
58
+ }
59
+ }
@@ -44,6 +44,66 @@ ruleTester.run("@definitelytyped/no-bad-reference", noBadReference, {
44
44
  ],
45
45
  filename: "types.d.ts",
46
46
  },
47
+ {
48
+ code: `/// <reference path="./v11" />`,
49
+ errors: [
50
+ {
51
+ column: 20,
52
+ endColumn: 25,
53
+ line: 1,
54
+ messageId: "referencePathOldVersion",
55
+ },
56
+ ],
57
+ filename: "types.d.ts",
58
+ },
59
+ {
60
+ code: `/// <reference path="./v11/index" />`,
61
+ errors: [
62
+ {
63
+ column: 20,
64
+ endColumn: 31,
65
+ line: 1,
66
+ messageId: "referencePathOldVersion",
67
+ },
68
+ ],
69
+ filename: "types.d.ts",
70
+ },
71
+ {
72
+ code: `/// <reference path="./v11/subdir/file" />`,
73
+ errors: [
74
+ {
75
+ column: 20,
76
+ endColumn: 37,
77
+ line: 1,
78
+ messageId: "referencePathOldVersion",
79
+ },
80
+ ],
81
+ filename: "types.d.ts",
82
+ },
83
+ {
84
+ code: `/// <reference path="./v0.1" />`,
85
+ errors: [
86
+ {
87
+ column: 20,
88
+ endColumn: 26,
89
+ line: 1,
90
+ messageId: "referencePathOldVersion",
91
+ },
92
+ ],
93
+ filename: "types.d.ts",
94
+ },
95
+ {
96
+ code: `/// <reference path="./v0.1/index" />`,
97
+ errors: [
98
+ {
99
+ column: 20,
100
+ endColumn: 32,
101
+ line: 1,
102
+ messageId: "referencePathOldVersion",
103
+ },
104
+ ],
105
+ filename: "types.d.ts",
106
+ },
47
107
  ],
48
108
  valid: [
49
109
  ``,
@@ -57,6 +117,14 @@ ruleTester.run("@definitelytyped/no-bad-reference", noBadReference, {
57
117
  code: `/// <reference path="./other" />`,
58
118
  filename: "types.d.ts",
59
119
  },
120
+ {
121
+ code: `/// <reference path="./v1gardenpath" />`,
122
+ filename: "types.d.ts",
123
+ },
124
+ {
125
+ code: `/// <reference path="./v1verb/other" />`,
126
+ filename: "types.d.ts",
127
+ },
60
128
  {
61
129
  code: `/// <reference path="other" />
62
130
  /// <reference path="other2" />`,
@@ -0,0 +1,72 @@
1
+ import { ESLintUtils } from "@typescript-eslint/utils";
2
+
3
+ import * as noImportDefaultOfDevDependencies from "../src/rules/no-import-of-dev-dependencies";
4
+
5
+ const ruleTester = new ESLintUtils.RuleTester({
6
+ parser: "@typescript-eslint/parser",
7
+ parserOptions: {
8
+ ecmaVersion: 2018,
9
+ },
10
+ });
11
+
12
+ ruleTester.run("@definitelytyped/no-import-of-dev-dependencies", noImportDefaultOfDevDependencies, {
13
+ invalid: [
14
+ {
15
+ filename: "index.d.ts",
16
+ code: `import eslint from "eslint"`,
17
+ errors: [
18
+ {
19
+ line: 1,
20
+ messageId: "noImportOfDevDependencies",
21
+ },
22
+ ],
23
+ },
24
+ // test @types/ removal
25
+ {
26
+ filename: "index.d.ts",
27
+ code: `import yargs from "yargs"`,
28
+ errors: [
29
+ {
30
+ line: 1,
31
+ messageId: "noImportOfDevDependencies",
32
+ },
33
+ ],
34
+ },
35
+ {
36
+ filename: "index.d.ts",
37
+ code: `/// <reference types="node" />`,
38
+ errors: [
39
+ {
40
+ line: 1,
41
+ messageId: "noReferenceOfDevDependencies",
42
+ },
43
+ ],
44
+ },
45
+ ],
46
+ valid: [
47
+ {
48
+ filename: "index.d.ts",
49
+ code: `import other from 'other'`,
50
+ },
51
+ {
52
+ filename: "types/yargs/index.d.ts",
53
+ code: `import self from "yargs"`,
54
+ },
55
+ {
56
+ filename: "index.d.ts",
57
+ code: `/// <reference types="other"/>`,
58
+ },
59
+ {
60
+ filename: "test.ts",
61
+ code: `import eslint from "eslint"`,
62
+ },
63
+ {
64
+ filename: "test.ts",
65
+ code: `import yargs from "yargs"`,
66
+ },
67
+ {
68
+ filename: "test.ts",
69
+ code: `/// <reference types="node" />`,
70
+ },
71
+ ],
72
+ });
@@ -0,0 +1,71 @@
1
+ import { ESLintUtils } from "@typescript-eslint/utils";
2
+
3
+ import * as noOldDtHeader from "../src/rules/no-old-dt-header";
4
+
5
+ const ruleTester = new ESLintUtils.RuleTester({
6
+ parser: "@typescript-eslint/parser",
7
+ });
8
+
9
+ ruleTester.run("@definitelytyped/no-old-dt-header", noOldDtHeader, {
10
+ invalid: [
11
+ {
12
+ code: `// Type definitions for AFRAME 1.2
13
+ // Project: https://aframe.io/
14
+ // Definitions by: Paul Shannon <https://github.com/devpaul>
15
+ // Roberto Ritger <https://github.com/bertoritger>
16
+ // Trygve Wastvedt <https://github.com/twastvedt>
17
+ // Definitions: https://github.com/DefinitelyTyped/DefinitelyTyped
18
+ // TypeScript Version: 4.4
19
+
20
+ /**
21
+ * Extended tests and examples available at https://github.com/devpaul/aframe-experiments.git
22
+ */
23
+
24
+ import * as anime from "animejs";
25
+ import * as three from "three";`,
26
+ errors: [
27
+ {
28
+ column: 1,
29
+ endColumn: 25,
30
+ line: 1,
31
+ messageId: "noOldDTHeader",
32
+ },
33
+ ],
34
+ filename: "index.d.ts",
35
+ },
36
+ {
37
+ code: `// Type definitions for AFRAME 1.2
38
+ // Definitions by: Paul Shannon <https://github.com/devpaul>`,
39
+ errors: [
40
+ {
41
+ column: 1,
42
+ endColumn: 25,
43
+ line: 1,
44
+ messageId: "noOldDTHeader",
45
+ },
46
+ ],
47
+ filename: "types.d.ts",
48
+ },
49
+ ],
50
+ valid: [
51
+ {
52
+ code: `// Type definitions for AFRAME 1.2
53
+ // Definitions by: Paul Shannon <https://github.com/devpaul>`,
54
+ filename: "test.ts",
55
+ },
56
+ {
57
+ code: `// Type definitions for AFRAME 1.2`,
58
+ filename: "types.d.ts",
59
+ },
60
+ {
61
+ code: `// Definitions by: Paul Shannon <https://github.com/devpaul>`,
62
+ filename: "types.d.ts",
63
+ },
64
+ {
65
+ code: `// A line before the old header
66
+ // Type definitions for AFRAME 1.2
67
+ // Definitions by: Paul Shannon <https://github.com/devpaul>`,
68
+ filename: "types.d.ts",
69
+ },
70
+ ],
71
+ });
@@ -28,6 +28,66 @@ ruleTester.run("@definitelytyped/no-self-import", dtHeader, {
28
28
  ],
29
29
  filename: "types/this-package/index.d.ts",
30
30
  },
31
+ {
32
+ code: `import old from "./v11"`,
33
+ errors: [
34
+ {
35
+ column: 1,
36
+ endColumn: 24,
37
+ line: 1,
38
+ messageId: "useOnlyCurrentVersion",
39
+ },
40
+ ],
41
+ filename: "types.d.ts",
42
+ },
43
+ {
44
+ code: `import old from "./v11/index"`,
45
+ errors: [
46
+ {
47
+ column: 1,
48
+ endColumn: 30,
49
+ line: 1,
50
+ messageId: "useOnlyCurrentVersion",
51
+ },
52
+ ],
53
+ filename: "types.d.ts",
54
+ },
55
+ {
56
+ code: `import old from "./v11/subdir/file"`,
57
+ errors: [
58
+ {
59
+ column: 1,
60
+ endColumn: 36,
61
+ line: 1,
62
+ messageId: "useOnlyCurrentVersion",
63
+ },
64
+ ],
65
+ filename: "types.d.ts",
66
+ },
67
+ {
68
+ code: `import old from "./v0.1"`,
69
+ errors: [
70
+ {
71
+ column: 1,
72
+ endColumn: 25,
73
+ line: 1,
74
+ messageId: "useOnlyCurrentVersion",
75
+ },
76
+ ],
77
+ filename: "types.d.ts",
78
+ },
79
+ {
80
+ code: `import old from "./v0.1/index"`,
81
+ errors: [
82
+ {
83
+ column: 1,
84
+ endColumn: 31,
85
+ line: 1,
86
+ messageId: "useOnlyCurrentVersion",
87
+ },
88
+ ],
89
+ filename: "types.d.ts",
90
+ },
31
91
  ],
32
92
  valid: [
33
93
  {
@@ -42,5 +102,13 @@ ruleTester.run("@definitelytyped/no-self-import", dtHeader, {
42
102
  code: `import myself from "this-package";`,
43
103
  filename: "types/grandparent/this-package/index.d.ts",
44
104
  },
105
+ {
106
+ code: `import old from "./v1gardenpath"`,
107
+ filename: "types.d.ts",
108
+ },
109
+ {
110
+ code: `import old from "./v1verb/other"`,
111
+ filename: "types.d.ts",
112
+ },
45
113
  ],
46
114
  });
@@ -0,0 +1,50 @@
1
+ import { ESLintUtils } from "@typescript-eslint/utils";
2
+ import path from "path";
3
+
4
+ import rule from "../src/rules/no-single-declare-module";
5
+
6
+ const ruleTester = new ESLintUtils.RuleTester({
7
+ parser: "@typescript-eslint/parser",
8
+ parserOptions: {
9
+ tsconfigRootDir: __dirname,
10
+ project: "./tsconfig.no-single-declare-module.json",
11
+ },
12
+ });
13
+
14
+ ruleTester.run("no-single-declare-module", rule, {
15
+ invalid: [
16
+ {
17
+ code: `
18
+ declare module "foo" {}
19
+
20
+ // Other global declarations don't affect this. They should go in "declare global".
21
+ interface I {}
22
+ `,
23
+ errors: [
24
+ {
25
+ line: 2,
26
+ messageId: "oneModuleDeclaration",
27
+ },
28
+ ],
29
+ },
30
+ ],
31
+ valid: [
32
+ {
33
+ code: `
34
+ import x from "x";
35
+ declare module "foo" {}
36
+ `,
37
+ },
38
+ {
39
+ code: `
40
+ declare module "foo" {}
41
+ declare module "bar" {}
42
+ `,
43
+ },
44
+ {
45
+ code: `
46
+ declare module "*.svg" {}
47
+ `,
48
+ },
49
+ ],
50
+ });
@@ -0,0 +1,7 @@
1
+ {
2
+ "compilerOptions": {
3
+ "strict": true,
4
+ "target": "esnext"
5
+ },
6
+ "files": ["file.ts"]
7
+ }