From 4896a8e3a6625b24881f910def00de45a148915e Mon Sep 17 00:00:00 2001 From: jaxee Date: Fri, 2 Nov 2018 15:20:53 -0400 Subject: [PATCH] adds no-all-mocks-methods rule --- docs/rules/jest/no-all-mocks-methods.md | 35 +++++++++++++++++ lib/rules/jest/no-all-mocks-methods.js | 35 +++++++++++++++++ tests/lib/rules/jest/no-all-mocks-methods.js | 41 ++++++++++++++++++++ 3 files changed, 111 insertions(+) create mode 100644 docs/rules/jest/no-all-mocks-methods.md create mode 100644 lib/rules/jest/no-all-mocks-methods.js create mode 100644 tests/lib/rules/jest/no-all-mocks-methods.js diff --git a/docs/rules/jest/no-all-mocks-methods.md b/docs/rules/jest/no-all-mocks-methods.md new file mode 100644 index 00000000..d995a364 --- /dev/null +++ b/docs/rules/jest/no-all-mocks-methods.md @@ -0,0 +1,35 @@ +# Disallows jest allMocks methods. + +This rule discourages the use of overly broad Jest methods such as `resetAllMocks`, `clearAllMocks`, `restoreAllMocks` and `resetModules`. + +## Rule Details + +These methods are discouraged because there should be explicit connections to the contents of your test file. Mocks should be reset/cleared/restored individually based on the purpose of your test suite. + +The following patterns are considered warnings: + +```js +jest.resetAllMocks(); +``` + +```js +jest.clearAllMocks(); +``` + +```js +jest.restoreAllMocks(); +``` + +```js +jest.resetModules(); +``` + +The following patterns are not warnings: + +```js +jest.mock(); +``` + +## Further Reading + +- [Shopify Jest Best Practices](https://github.com/Shopify/web-foundation/blob/master/Best%20practices/Jest.md#best-practices) diff --git a/lib/rules/jest/no-all-mocks-methods.js b/lib/rules/jest/no-all-mocks-methods.js new file mode 100644 index 00000000..a2091f15 --- /dev/null +++ b/lib/rules/jest/no-all-mocks-methods.js @@ -0,0 +1,35 @@ +module.exports = { + meta: { + docs: { + description: 'Disallows jest allMocks methods.', + category: 'Best Practices', + recommended: false, + uri: + 'https://github.com/Shopify/eslint-plugin-shopify/blob/master/docs/rules/jest/no-all-mocks-methods.md', + }, + }, + + create(context) { + return { + Identifier(node) { + if (isInvalidMocks(node.name)) { + context.report({ + node, + message: + 'Do not use {{method}} or related methods that are not explicit to your test. Instead, target individual mocks.', + data: {method: node.name}, + }); + } + }, + }; + }, +}; + +function isInvalidMocks(name) { + return [ + 'resetAllMocks', + 'clearAllMocks', + 'restoreAllMocks', + 'resetModules', + ].some((method) => method === name); +} diff --git a/tests/lib/rules/jest/no-all-mocks-methods.js b/tests/lib/rules/jest/no-all-mocks-methods.js new file mode 100644 index 00000000..cd192f48 --- /dev/null +++ b/tests/lib/rules/jest/no-all-mocks-methods.js @@ -0,0 +1,41 @@ +const {RuleTester} = require('eslint'); +const rule = require('../../../../lib/rules/jest/no-all-mocks-methods'); + +const ruleTester = new RuleTester(); +function errorWithMethodName(name) { + return [ + { + type: 'Identifier', + message: `Do not use ${name} or related methods that are not explicit to your test. Instead, target individual mocks.`, + }, + ]; +} + +ruleTester.run('no-all-mocks-methods', rule, { + valid: [ + { + code: `jest.mock()`, + }, + { + code: `jest.fn()`, + }, + ], + invalid: [ + { + code: 'jest.resetAllMocks()', + errors: errorWithMethodName('resetAllMocks'), + }, + { + code: 'jest.clearAllMocks()', + errors: errorWithMethodName('clearAllMocks'), + }, + { + code: 'jest.restoreAllMocks()', + errors: errorWithMethodName('restoreAllMocks'), + }, + { + code: 'jest.resetModules()', + errors: errorWithMethodName('resetModules'), + }, + ], +});