@depup/eslint-plugin-jest 29.15.1-depup.0

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 (158) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +31 -0
  3. package/changes.json +10 -0
  4. package/docs/rules/consistent-test-it.md +96 -0
  5. package/docs/rules/expect-expect.md +152 -0
  6. package/docs/rules/max-expects.md +78 -0
  7. package/docs/rules/max-nested-describe.md +134 -0
  8. package/docs/rules/no-alias-methods.md +57 -0
  9. package/docs/rules/no-commented-out-tests.md +68 -0
  10. package/docs/rules/no-conditional-expect.md +142 -0
  11. package/docs/rules/no-conditional-in-test.md +123 -0
  12. package/docs/rules/no-confusing-set-timeout.md +64 -0
  13. package/docs/rules/no-deprecated-functions.md +59 -0
  14. package/docs/rules/no-disabled-tests.md +72 -0
  15. package/docs/rules/no-done-callback.md +100 -0
  16. package/docs/rules/no-duplicate-hooks.md +79 -0
  17. package/docs/rules/no-error-equal.md +37 -0
  18. package/docs/rules/no-export.md +52 -0
  19. package/docs/rules/no-focused-tests.md +67 -0
  20. package/docs/rules/no-hooks.md +178 -0
  21. package/docs/rules/no-identical-title.md +59 -0
  22. package/docs/rules/no-interpolation-in-snapshots.md +67 -0
  23. package/docs/rules/no-jasmine-globals.md +69 -0
  24. package/docs/rules/no-large-snapshots.md +180 -0
  25. package/docs/rules/no-mocks-import.md +34 -0
  26. package/docs/rules/no-restricted-jest-methods.md +53 -0
  27. package/docs/rules/no-restricted-matchers.md +64 -0
  28. package/docs/rules/no-standalone-expect.md +106 -0
  29. package/docs/rules/no-test-prefixes.md +42 -0
  30. package/docs/rules/no-test-return-statement.md +50 -0
  31. package/docs/rules/no-unnecessary-assertion.md +41 -0
  32. package/docs/rules/no-unneeded-async-expect-function.md +41 -0
  33. package/docs/rules/no-untyped-mock-factory.md +74 -0
  34. package/docs/rules/padding-around-after-all-blocks.md +34 -0
  35. package/docs/rules/padding-around-after-each-blocks.md +38 -0
  36. package/docs/rules/padding-around-all.md +20 -0
  37. package/docs/rules/padding-around-before-all-blocks.md +37 -0
  38. package/docs/rules/padding-around-before-each-blocks.md +38 -0
  39. package/docs/rules/padding-around-describe-blocks.md +42 -0
  40. package/docs/rules/padding-around-expect-groups.md +44 -0
  41. package/docs/rules/padding-around-test-blocks.md +48 -0
  42. package/docs/rules/prefer-called-with.md +39 -0
  43. package/docs/rules/prefer-comparison-matcher.md +62 -0
  44. package/docs/rules/prefer-each.md +58 -0
  45. package/docs/rules/prefer-ending-with-an-expect.md +170 -0
  46. package/docs/rules/prefer-equality-matcher.md +36 -0
  47. package/docs/rules/prefer-expect-assertions.md +230 -0
  48. package/docs/rules/prefer-expect-resolves.md +62 -0
  49. package/docs/rules/prefer-hooks-in-order.md +137 -0
  50. package/docs/rules/prefer-hooks-on-top.md +124 -0
  51. package/docs/rules/prefer-importing-jest-globals.md +85 -0
  52. package/docs/rules/prefer-jest-mocked.md +40 -0
  53. package/docs/rules/prefer-lowercase-title.md +128 -0
  54. package/docs/rules/prefer-mock-promise-shorthand.md +41 -0
  55. package/docs/rules/prefer-mock-return-shorthand.md +50 -0
  56. package/docs/rules/prefer-snapshot-hint.md +192 -0
  57. package/docs/rules/prefer-spy-on.md +46 -0
  58. package/docs/rules/prefer-strict-equal.md +29 -0
  59. package/docs/rules/prefer-to-be.md +63 -0
  60. package/docs/rules/prefer-to-contain.md +53 -0
  61. package/docs/rules/prefer-to-have-been-called-times.md +43 -0
  62. package/docs/rules/prefer-to-have-been-called.md +35 -0
  63. package/docs/rules/prefer-to-have-length.md +41 -0
  64. package/docs/rules/prefer-todo.md +33 -0
  65. package/docs/rules/require-hook.md +187 -0
  66. package/docs/rules/require-to-throw-message.md +43 -0
  67. package/docs/rules/require-top-level-describe.md +86 -0
  68. package/docs/rules/unbound-method.md +61 -0
  69. package/docs/rules/valid-describe-callback.md +69 -0
  70. package/docs/rules/valid-expect-in-promise.md +79 -0
  71. package/docs/rules/valid-expect-with-promise.md +43 -0
  72. package/docs/rules/valid-expect.md +155 -0
  73. package/docs/rules/valid-mock-module-path.md +72 -0
  74. package/docs/rules/valid-title.md +319 -0
  75. package/index.d.ts +28 -0
  76. package/lib/globals.json +15 -0
  77. package/lib/index.js +85 -0
  78. package/lib/rules/consistent-test-it.js +101 -0
  79. package/lib/rules/expect-expect.js +102 -0
  80. package/lib/rules/max-expects.js +70 -0
  81. package/lib/rules/max-nested-describe.js +59 -0
  82. package/lib/rules/no-alias-methods.js +62 -0
  83. package/lib/rules/no-commented-out-tests.js +44 -0
  84. package/lib/rules/no-conditional-expect.js +80 -0
  85. package/lib/rules/no-conditional-in-test.js +63 -0
  86. package/lib/rules/no-confusing-set-timeout.js +61 -0
  87. package/lib/rules/no-deprecated-functions.js +81 -0
  88. package/lib/rules/no-disabled-tests.js +57 -0
  89. package/lib/rules/no-done-callback.js +120 -0
  90. package/lib/rules/no-duplicate-hooks.js +52 -0
  91. package/lib/rules/no-error-equal.js +41 -0
  92. package/lib/rules/no-export.js +61 -0
  93. package/lib/rules/no-focused-tests.js +63 -0
  94. package/lib/rules/no-hooks.js +51 -0
  95. package/lib/rules/no-identical-title.js +73 -0
  96. package/lib/rules/no-interpolation-in-snapshots.js +43 -0
  97. package/lib/rules/no-jasmine-globals.js +140 -0
  98. package/lib/rules/no-large-snapshots.js +100 -0
  99. package/lib/rules/no-mocks-import.js +46 -0
  100. package/lib/rules/no-restricted-jest-methods.js +53 -0
  101. package/lib/rules/no-restricted-matchers.js +60 -0
  102. package/lib/rules/no-standalone-expect.js +114 -0
  103. package/lib/rules/no-test-prefixes.js +48 -0
  104. package/lib/rules/no-test-return-statement.js +62 -0
  105. package/lib/rules/no-unnecessary-assertion.js +87 -0
  106. package/lib/rules/no-unneeded-async-expect-function.js +57 -0
  107. package/lib/rules/no-untyped-mock-factory.js +61 -0
  108. package/lib/rules/padding-around-after-all-blocks.js +17 -0
  109. package/lib/rules/padding-around-after-each-blocks.js +17 -0
  110. package/lib/rules/padding-around-all.js +15 -0
  111. package/lib/rules/padding-around-before-all-blocks.js +17 -0
  112. package/lib/rules/padding-around-before-each-blocks.js +17 -0
  113. package/lib/rules/padding-around-describe-blocks.js +17 -0
  114. package/lib/rules/padding-around-expect-groups.js +21 -0
  115. package/lib/rules/padding-around-test-blocks.js +17 -0
  116. package/lib/rules/prefer-called-with.js +47 -0
  117. package/lib/rules/prefer-comparison-matcher.js +111 -0
  118. package/lib/rules/prefer-each.js +77 -0
  119. package/lib/rules/prefer-ending-with-an-expect.js +102 -0
  120. package/lib/rules/prefer-equality-matcher.js +87 -0
  121. package/lib/rules/prefer-expect-assertions.js +237 -0
  122. package/lib/rules/prefer-expect-resolves.js +47 -0
  123. package/lib/rules/prefer-hooks-in-order.js +67 -0
  124. package/lib/rules/prefer-hooks-on-top.js +41 -0
  125. package/lib/rules/prefer-importing-jest-globals.js +126 -0
  126. package/lib/rules/prefer-jest-mocked.js +66 -0
  127. package/lib/rules/prefer-lowercase-title.js +128 -0
  128. package/lib/rules/prefer-mock-promise-shorthand.js +88 -0
  129. package/lib/rules/prefer-mock-return-shorthand.js +122 -0
  130. package/lib/rules/prefer-snapshot-hint.js +111 -0
  131. package/lib/rules/prefer-spy-on.js +80 -0
  132. package/lib/rules/prefer-strict-equal.js +46 -0
  133. package/lib/rules/prefer-to-be.js +98 -0
  134. package/lib/rules/prefer-to-contain.js +82 -0
  135. package/lib/rules/prefer-to-have-been-called-times.js +70 -0
  136. package/lib/rules/prefer-to-have-been-called.js +59 -0
  137. package/lib/rules/prefer-to-have-length.js +57 -0
  138. package/lib/rules/prefer-todo.js +72 -0
  139. package/lib/rules/require-hook.js +93 -0
  140. package/lib/rules/require-to-throw-message.js +45 -0
  141. package/lib/rules/require-top-level-describe.js +86 -0
  142. package/lib/rules/unbound-method.js +86 -0
  143. package/lib/rules/utils/accessors.js +127 -0
  144. package/lib/rules/utils/ast-utils.js +59 -0
  145. package/lib/rules/utils/detectJestVersion.js +24 -0
  146. package/lib/rules/utils/followTypeAssertionChain.js +10 -0
  147. package/lib/rules/utils/index.js +71 -0
  148. package/lib/rules/utils/misc.js +168 -0
  149. package/lib/rules/utils/padding.js +308 -0
  150. package/lib/rules/utils/parseJestFnCall.js +325 -0
  151. package/lib/rules/utils/ts.js +73 -0
  152. package/lib/rules/valid-describe-callback.js +94 -0
  153. package/lib/rules/valid-expect-in-promise.js +311 -0
  154. package/lib/rules/valid-expect-with-promise.js +54 -0
  155. package/lib/rules/valid-expect.js +302 -0
  156. package/lib/rules/valid-mock-module-path.js +90 -0
  157. package/lib/rules/valid-title.js +252 -0
  158. package/package.json +164 -0
@@ -0,0 +1,101 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("@typescript-eslint/utils");
8
+ var _utils2 = require("./utils");
9
+ const buildFixer = (callee, nodeName, preferredTestKeyword) => fixer => [fixer.replaceText(callee.type === _utils.AST_NODE_TYPES.MemberExpression ? callee.object : callee, getPreferredNodeName(nodeName, preferredTestKeyword))];
10
+ var _default = exports.default = (0, _utils2.createRule)({
11
+ name: __filename,
12
+ meta: {
13
+ docs: {
14
+ description: 'Enforce `test` and `it` usage conventions'
15
+ },
16
+ fixable: 'code',
17
+ messages: {
18
+ consistentMethod: "Prefer using '{{ testKeyword }}' instead of '{{ oppositeTestKeyword }}'",
19
+ consistentMethodWithinDescribe: "Prefer using '{{ testKeywordWithinDescribe }}' instead of '{{ oppositeTestKeyword }}' within describe"
20
+ },
21
+ schema: [{
22
+ type: 'object',
23
+ properties: {
24
+ fn: {
25
+ type: 'string',
26
+ enum: [_utils2.TestCaseName.it, _utils2.TestCaseName.test]
27
+ },
28
+ withinDescribe: {
29
+ type: 'string',
30
+ enum: [_utils2.TestCaseName.it, _utils2.TestCaseName.test]
31
+ }
32
+ },
33
+ additionalProperties: false
34
+ }],
35
+ type: 'suggestion'
36
+ },
37
+ defaultOptions: [{
38
+ fn: _utils2.TestCaseName.test,
39
+ withinDescribe: _utils2.TestCaseName.it
40
+ }],
41
+ create(context) {
42
+ const configObj = context.options[0] || {};
43
+ const testKeyword = configObj.fn || _utils2.TestCaseName.test;
44
+ const testKeywordWithinDescribe = configObj.withinDescribe || configObj.fn || _utils2.TestCaseName.it;
45
+ let describeNestingLevel = 0;
46
+ return {
47
+ CallExpression(node) {
48
+ const jestFnCall = (0, _utils2.parseJestFnCall)(node, context);
49
+ if (!jestFnCall) {
50
+ return;
51
+ }
52
+ if (jestFnCall.type === 'describe') {
53
+ describeNestingLevel++;
54
+ return;
55
+ }
56
+ const funcNode = node.callee.type === _utils.AST_NODE_TYPES.TaggedTemplateExpression ? node.callee.tag : node.callee.type === _utils.AST_NODE_TYPES.CallExpression ? node.callee.callee : node.callee;
57
+ if (jestFnCall.type === 'test' && describeNestingLevel === 0 && !jestFnCall.name.endsWith(testKeyword)) {
58
+ const oppositeTestKeyword = getOppositeTestKeyword(testKeyword);
59
+ context.report({
60
+ messageId: 'consistentMethod',
61
+ node: node.callee,
62
+ data: {
63
+ testKeyword,
64
+ oppositeTestKeyword
65
+ },
66
+ fix: buildFixer(funcNode, jestFnCall.name, testKeyword)
67
+ });
68
+ }
69
+ if (jestFnCall.type === 'test' && describeNestingLevel > 0 && !jestFnCall.name.endsWith(testKeywordWithinDescribe)) {
70
+ const oppositeTestKeyword = getOppositeTestKeyword(testKeywordWithinDescribe);
71
+ context.report({
72
+ messageId: 'consistentMethodWithinDescribe',
73
+ node: node.callee,
74
+ data: {
75
+ testKeywordWithinDescribe,
76
+ oppositeTestKeyword
77
+ },
78
+ fix: buildFixer(funcNode, jestFnCall.name, testKeywordWithinDescribe)
79
+ });
80
+ }
81
+ },
82
+ 'CallExpression:exit'(node) {
83
+ if ((0, _utils2.isTypeOfJestFnCall)(node, context, ['describe'])) {
84
+ describeNestingLevel--;
85
+ }
86
+ }
87
+ };
88
+ }
89
+ });
90
+ function getPreferredNodeName(nodeName, preferredTestKeyword) {
91
+ if (nodeName === _utils2.TestCaseName.fit) {
92
+ return 'test.only';
93
+ }
94
+ return nodeName.startsWith('f') || nodeName.startsWith('x') ? nodeName.charAt(0) + preferredTestKeyword : preferredTestKeyword;
95
+ }
96
+ function getOppositeTestKeyword(test) {
97
+ if (test === _utils2.TestCaseName.test) {
98
+ return _utils2.TestCaseName.it;
99
+ }
100
+ return _utils2.TestCaseName.test;
101
+ }
@@ -0,0 +1,102 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("@typescript-eslint/utils");
8
+ var _utils2 = require("./utils");
9
+ /*
10
+ * This implementation is adapted from eslint-plugin-jasmine.
11
+ * MIT license, Remco Haszing.
12
+ */
13
+
14
+ /**
15
+ * Checks if node names returned by getNodeName matches any of the given star patterns
16
+ * Pattern examples:
17
+ * request.*.expect
18
+ * request.**.expect
19
+ * request.**.expect*
20
+ */
21
+ function matchesAssertFunctionName(nodeName, patterns) {
22
+ return patterns.some(p => new RegExp(`^${p.split('.').map(x => {
23
+ if (x === '**') {
24
+ return '[a-z\\d\\.]*';
25
+ }
26
+ return x.replace(/\*/gu, '[a-z\\d]*');
27
+ }).join('\\.')}(\\.|$)`, 'ui').test(nodeName));
28
+ }
29
+ var _default = exports.default = (0, _utils2.createRule)({
30
+ name: __filename,
31
+ meta: {
32
+ docs: {
33
+ description: 'Enforce assertion to be made in a test body'
34
+ },
35
+ messages: {
36
+ noAssertions: 'Test has no assertions'
37
+ },
38
+ schema: [{
39
+ type: 'object',
40
+ properties: {
41
+ assertFunctionNames: {
42
+ type: 'array',
43
+ items: {
44
+ type: 'string'
45
+ }
46
+ },
47
+ additionalTestBlockFunctions: {
48
+ type: 'array',
49
+ items: {
50
+ type: 'string'
51
+ }
52
+ }
53
+ },
54
+ additionalProperties: false
55
+ }],
56
+ type: 'suggestion'
57
+ },
58
+ defaultOptions: [{
59
+ assertFunctionNames: ['expect'],
60
+ additionalTestBlockFunctions: []
61
+ }],
62
+ create(context, [{
63
+ assertFunctionNames = ['expect'],
64
+ additionalTestBlockFunctions = []
65
+ }]) {
66
+ const unchecked = [];
67
+ function checkCallExpressionUsed(nodes) {
68
+ for (const node of nodes) {
69
+ const index = node.type === _utils.AST_NODE_TYPES.CallExpression ? unchecked.indexOf(node) : -1;
70
+ if (node.type === _utils.AST_NODE_TYPES.FunctionDeclaration) {
71
+ const declaredVariables = context.sourceCode.getDeclaredVariables(node);
72
+ const testCallExpressions = (0, _utils2.getTestCallExpressionsFromDeclaredVariables)(declaredVariables, context);
73
+ checkCallExpressionUsed(testCallExpressions);
74
+ }
75
+ if (index !== -1) {
76
+ unchecked.splice(index, 1);
77
+ break;
78
+ }
79
+ }
80
+ }
81
+ return {
82
+ CallExpression(node) {
83
+ const name = (0, _utils2.getNodeName)(node.callee) ?? '';
84
+ if ((0, _utils2.isTypeOfJestFnCall)(node, context, ['test']) || additionalTestBlockFunctions.includes(name)) {
85
+ if (node.callee.type === _utils.AST_NODE_TYPES.MemberExpression && (0, _utils2.isSupportedAccessor)(node.callee.property, 'todo')) {
86
+ return;
87
+ }
88
+ unchecked.push(node);
89
+ } else if (matchesAssertFunctionName(name, assertFunctionNames)) {
90
+ // Return early in case of nested `it` statements.
91
+ checkCallExpressionUsed(context.sourceCode.getAncestors(node));
92
+ }
93
+ },
94
+ 'Program:exit'() {
95
+ unchecked.forEach(node => context.report({
96
+ messageId: 'noAssertions',
97
+ node: node.callee
98
+ }));
99
+ }
100
+ };
101
+ }
102
+ });
@@ -0,0 +1,70 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("@typescript-eslint/utils");
8
+ var _utils2 = require("./utils");
9
+ var _default = exports.default = (0, _utils2.createRule)({
10
+ name: __filename,
11
+ meta: {
12
+ docs: {
13
+ description: 'Enforces a maximum number assertion calls in a test body'
14
+ },
15
+ messages: {
16
+ exceededMaxAssertion: 'Too many assertion calls ({{ count }}) - maximum allowed is {{ max }}'
17
+ },
18
+ type: 'suggestion',
19
+ schema: [{
20
+ type: 'object',
21
+ properties: {
22
+ max: {
23
+ type: 'integer',
24
+ minimum: 1
25
+ }
26
+ },
27
+ additionalProperties: false
28
+ }]
29
+ },
30
+ defaultOptions: [{
31
+ max: 5
32
+ }],
33
+ create(context, [{
34
+ max
35
+ }]) {
36
+ let count = 0;
37
+ const maybeResetCount = node => {
38
+ const isTestFn = node.parent.type !== _utils.AST_NODE_TYPES.CallExpression || (0, _utils2.isTypeOfJestFnCall)(node.parent, context, ['test']);
39
+ if (isTestFn) {
40
+ count = 0;
41
+ }
42
+ };
43
+ return {
44
+ FunctionExpression: maybeResetCount,
45
+ 'FunctionExpression:exit': maybeResetCount,
46
+ ArrowFunctionExpression: maybeResetCount,
47
+ 'ArrowFunctionExpression:exit': maybeResetCount,
48
+ CallExpression(node) {
49
+ const jestFnCall = (0, _utils2.parseJestFnCall)(node, context);
50
+ if (jestFnCall?.type === 'test') {
51
+ count = 0;
52
+ }
53
+ if (jestFnCall?.type !== 'expect' || jestFnCall.head.node.parent.type === _utils.AST_NODE_TYPES.MemberExpression) {
54
+ return;
55
+ }
56
+ count += 1;
57
+ if (count > max) {
58
+ context.report({
59
+ node,
60
+ messageId: 'exceededMaxAssertion',
61
+ data: {
62
+ count,
63
+ max
64
+ }
65
+ });
66
+ }
67
+ }
68
+ };
69
+ }
70
+ });
@@ -0,0 +1,59 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("./utils");
8
+ var _default = exports.default = (0, _utils.createRule)({
9
+ name: __filename,
10
+ meta: {
11
+ docs: {
12
+ description: 'Enforces a maximum depth to nested describe calls'
13
+ },
14
+ messages: {
15
+ exceededMaxDepth: 'Too many nested describe calls ({{ depth }}) - maximum allowed is {{ max }}'
16
+ },
17
+ type: 'suggestion',
18
+ schema: [{
19
+ type: 'object',
20
+ properties: {
21
+ max: {
22
+ type: 'integer',
23
+ minimum: 0
24
+ }
25
+ },
26
+ additionalProperties: false
27
+ }]
28
+ },
29
+ defaultOptions: [{
30
+ max: 5
31
+ }],
32
+ create(context, [{
33
+ max
34
+ }]) {
35
+ const describes = [];
36
+ return {
37
+ CallExpression(node) {
38
+ if ((0, _utils.isTypeOfJestFnCall)(node, context, ['describe'])) {
39
+ describes.unshift(node);
40
+ if (describes.length > max) {
41
+ context.report({
42
+ node,
43
+ messageId: 'exceededMaxDepth',
44
+ data: {
45
+ depth: describes.length,
46
+ max
47
+ }
48
+ });
49
+ }
50
+ }
51
+ },
52
+ 'CallExpression:exit'(node) {
53
+ if (describes[0] === node) {
54
+ describes.shift();
55
+ }
56
+ }
57
+ };
58
+ }
59
+ });
@@ -0,0 +1,62 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("./utils");
8
+ var _default = exports.default = (0, _utils.createRule)({
9
+ name: __filename,
10
+ meta: {
11
+ docs: {
12
+ description: 'Disallow alias methods'
13
+ },
14
+ messages: {
15
+ replaceAlias: `Replace {{ alias }}() with its canonical name of {{ canonical }}()`
16
+ },
17
+ fixable: 'code',
18
+ type: 'suggestion',
19
+ schema: []
20
+ },
21
+ defaultOptions: [],
22
+ create(context) {
23
+ // map of jest matcher aliases & their canonical names
24
+ const methodNames = {
25
+ toBeCalled: 'toHaveBeenCalled',
26
+ toBeCalledTimes: 'toHaveBeenCalledTimes',
27
+ toBeCalledWith: 'toHaveBeenCalledWith',
28
+ lastCalledWith: 'toHaveBeenLastCalledWith',
29
+ nthCalledWith: 'toHaveBeenNthCalledWith',
30
+ toReturn: 'toHaveReturned',
31
+ toReturnTimes: 'toHaveReturnedTimes',
32
+ toReturnWith: 'toHaveReturnedWith',
33
+ lastReturnedWith: 'toHaveLastReturnedWith',
34
+ nthReturnedWith: 'toHaveNthReturnedWith',
35
+ toThrowError: 'toThrow'
36
+ };
37
+ return {
38
+ CallExpression(node) {
39
+ const jestFnCall = (0, _utils.parseJestFnCall)(node, context);
40
+ if (jestFnCall?.type !== 'expect') {
41
+ return;
42
+ }
43
+ const {
44
+ matcher
45
+ } = jestFnCall;
46
+ const alias = (0, _utils.getAccessorValue)(matcher);
47
+ if (alias in methodNames) {
48
+ const canonical = methodNames[alias];
49
+ context.report({
50
+ messageId: 'replaceAlias',
51
+ data: {
52
+ alias,
53
+ canonical
54
+ },
55
+ node: matcher,
56
+ fix: fixer => [(0, _utils.replaceAccessorFixer)(fixer, matcher, canonical)]
57
+ });
58
+ }
59
+ }
60
+ };
61
+ }
62
+ });
@@ -0,0 +1,44 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("./utils");
8
+ function hasTests(node) {
9
+ return /^\s*[xf]?(test|it|describe)(\.\w+|\[['"]\w+['"]\])?\s*\(/mu.test(node.value);
10
+ }
11
+ var _default = exports.default = (0, _utils.createRule)({
12
+ name: __filename,
13
+ meta: {
14
+ docs: {
15
+ description: 'Disallow commented out tests'
16
+ },
17
+ messages: {
18
+ commentedTests: 'Do not comment out tests'
19
+ },
20
+ schema: [],
21
+ type: 'suggestion'
22
+ },
23
+ defaultOptions: [],
24
+ create(context) {
25
+ const {
26
+ sourceCode
27
+ } = context;
28
+ function checkNode(node) {
29
+ if (!hasTests(node)) {
30
+ return;
31
+ }
32
+ context.report({
33
+ messageId: 'commentedTests',
34
+ node
35
+ });
36
+ }
37
+ return {
38
+ Program() {
39
+ const comments = sourceCode.getAllComments();
40
+ comments.forEach(checkNode);
41
+ }
42
+ };
43
+ }
44
+ });
@@ -0,0 +1,80 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("@typescript-eslint/utils");
8
+ var _utils2 = require("./utils");
9
+ const isCatchCall = node => node.callee.type === _utils.AST_NODE_TYPES.MemberExpression && (0, _utils2.isSupportedAccessor)(node.callee.property, 'catch');
10
+ var _default = exports.default = (0, _utils2.createRule)({
11
+ name: __filename,
12
+ meta: {
13
+ docs: {
14
+ description: 'Disallow calling `expect` conditionally'
15
+ },
16
+ messages: {
17
+ conditionalExpect: 'Avoid calling `expect` conditionally`'
18
+ },
19
+ type: 'problem',
20
+ schema: []
21
+ },
22
+ defaultOptions: [],
23
+ create(context) {
24
+ let conditionalDepth = 0;
25
+ let inTestCase = false;
26
+ let inPromiseCatch = false;
27
+ const increaseConditionalDepth = () => inTestCase && conditionalDepth++;
28
+ const decreaseConditionalDepth = () => inTestCase && conditionalDepth--;
29
+ return {
30
+ FunctionDeclaration(node) {
31
+ const declaredVariables = context.sourceCode.getDeclaredVariables(node);
32
+ const testCallExpressions = (0, _utils2.getTestCallExpressionsFromDeclaredVariables)(declaredVariables, context);
33
+ if (testCallExpressions.length > 0) {
34
+ inTestCase = true;
35
+ }
36
+ },
37
+ CallExpression(node) {
38
+ const {
39
+ type: jestFnCallType
40
+ } = (0, _utils2.parseJestFnCall)(node, context) ?? {};
41
+ if (jestFnCallType === 'test') {
42
+ inTestCase = true;
43
+ }
44
+ if (isCatchCall(node)) {
45
+ inPromiseCatch = true;
46
+ }
47
+ if (inTestCase && jestFnCallType === 'expect' && conditionalDepth > 0) {
48
+ context.report({
49
+ messageId: 'conditionalExpect',
50
+ node
51
+ });
52
+ }
53
+ if (inPromiseCatch && jestFnCallType === 'expect') {
54
+ context.report({
55
+ messageId: 'conditionalExpect',
56
+ node
57
+ });
58
+ }
59
+ },
60
+ 'CallExpression:exit'(node) {
61
+ if ((0, _utils2.isTypeOfJestFnCall)(node, context, ['test'])) {
62
+ inTestCase = false;
63
+ }
64
+ if (isCatchCall(node)) {
65
+ inPromiseCatch = false;
66
+ }
67
+ },
68
+ CatchClause: increaseConditionalDepth,
69
+ 'CatchClause:exit': decreaseConditionalDepth,
70
+ IfStatement: increaseConditionalDepth,
71
+ 'IfStatement:exit': decreaseConditionalDepth,
72
+ SwitchStatement: increaseConditionalDepth,
73
+ 'SwitchStatement:exit': decreaseConditionalDepth,
74
+ ConditionalExpression: increaseConditionalDepth,
75
+ 'ConditionalExpression:exit': decreaseConditionalDepth,
76
+ LogicalExpression: increaseConditionalDepth,
77
+ 'LogicalExpression:exit': decreaseConditionalDepth
78
+ };
79
+ }
80
+ });
@@ -0,0 +1,63 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("./utils");
8
+ var _default = exports.default = (0, _utils.createRule)({
9
+ name: __filename,
10
+ meta: {
11
+ docs: {
12
+ description: 'Disallow conditional logic in tests'
13
+ },
14
+ messages: {
15
+ conditionalInTest: 'Avoid having conditionals in tests'
16
+ },
17
+ type: 'problem',
18
+ schema: [{
19
+ type: 'object',
20
+ properties: {
21
+ allowOptionalChaining: {
22
+ type: 'boolean'
23
+ }
24
+ },
25
+ additionalProperties: false
26
+ }]
27
+ },
28
+ defaultOptions: [{
29
+ allowOptionalChaining: true
30
+ }],
31
+ create(context, [{
32
+ allowOptionalChaining
33
+ }]) {
34
+ let inTestCase = false;
35
+ const maybeReportConditional = node => {
36
+ if (inTestCase) {
37
+ context.report({
38
+ messageId: 'conditionalInTest',
39
+ node
40
+ });
41
+ }
42
+ };
43
+ return {
44
+ CallExpression(node) {
45
+ if ((0, _utils.isTypeOfJestFnCall)(node, context, ['test'])) {
46
+ inTestCase = true;
47
+ }
48
+ },
49
+ 'CallExpression:exit'(node) {
50
+ if ((0, _utils.isTypeOfJestFnCall)(node, context, ['test'])) {
51
+ inTestCase = false;
52
+ }
53
+ },
54
+ IfStatement: maybeReportConditional,
55
+ SwitchStatement: maybeReportConditional,
56
+ ConditionalExpression: maybeReportConditional,
57
+ LogicalExpression: maybeReportConditional,
58
+ ...(!allowOptionalChaining && {
59
+ ChainExpression: maybeReportConditional
60
+ })
61
+ };
62
+ }
63
+ });
@@ -0,0 +1,61 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("./utils");
8
+ function isJestSetTimeout(jestFnCall) {
9
+ return jestFnCall.type === 'jest' && jestFnCall.members.length === 1 && (0, _utils.isIdentifier)(jestFnCall.members[0], 'setTimeout');
10
+ }
11
+ var _default = exports.default = (0, _utils.createRule)({
12
+ name: __filename,
13
+ meta: {
14
+ docs: {
15
+ description: 'Disallow confusing usages of jest.setTimeout'
16
+ },
17
+ messages: {
18
+ globalSetTimeout: '`jest.setTimeout` should be call in `global` scope',
19
+ multipleSetTimeouts: 'Do not call `jest.setTimeout` multiple times, as only the last call will have an effect',
20
+ orderSetTimeout: '`jest.setTimeout` should be placed before any other jest methods'
21
+ },
22
+ type: 'problem',
23
+ schema: []
24
+ },
25
+ defaultOptions: [],
26
+ create(context) {
27
+ let seenJestTimeout = false;
28
+ let shouldEmitOrderSetTimeout = false;
29
+ return {
30
+ CallExpression(node) {
31
+ const jestFnCall = (0, _utils.parseJestFnCall)(node, context);
32
+ if (!jestFnCall) {
33
+ return;
34
+ }
35
+ if (!isJestSetTimeout(jestFnCall)) {
36
+ shouldEmitOrderSetTimeout = true;
37
+ return;
38
+ }
39
+ if (!['global', 'module'].includes(context.sourceCode.getScope(node).type)) {
40
+ context.report({
41
+ messageId: 'globalSetTimeout',
42
+ node
43
+ });
44
+ }
45
+ if (shouldEmitOrderSetTimeout) {
46
+ context.report({
47
+ messageId: 'orderSetTimeout',
48
+ node
49
+ });
50
+ }
51
+ if (seenJestTimeout) {
52
+ context.report({
53
+ messageId: 'multipleSetTimeouts',
54
+ node
55
+ });
56
+ }
57
+ seenJestTimeout = true;
58
+ }
59
+ };
60
+ }
61
+ });