33 *
44 * This source code is licensed under the MIT license found in the
55 * LICENSE file in the root directory of this source tree.
6+ *
7+ * @jest -environment node
68 */
79
810'use strict' ;
911
10- const ESLintTester = require ( 'eslint' ) . RuleTester ;
12+ const ESLintTesterV7 = require ( 'eslint-v7' ) . RuleTester ;
13+ const ESLintTesterV9 = require ( 'eslint-v9' ) . RuleTester ;
1114const ReactHooksESLintPlugin = require ( 'eslint-plugin-react-hooks' ) ;
1215const ReactHooksESLintRule = ReactHooksESLintPlugin . rules [ 'exhaustive-deps' ] ;
1316
@@ -4673,17 +4676,8 @@ const tests = {
46734676 return <div ref={myRef} />;
46744677 }
46754678 ` ,
4676- output : `
4677- function MyComponent() {
4678- const myRef = useRef();
4679- useLayoutEffect_SAFE_FOR_SSR(() => {
4680- const handleMove = () => {};
4681- myRef.current.addEventListener('mousemove', handleMove);
4682- return () => myRef.current.removeEventListener('mousemove', handleMove);
4683- });
4684- return <div ref={myRef} />;
4685- }
4686- ` ,
4679+ // No changes
4680+ output : null ,
46874681 errors : [
46884682 `The ref value 'myRef.current' will likely have changed by the time ` +
46894683 `this effect cleanup function runs. If this ref points to a node ` +
@@ -7101,6 +7095,19 @@ const tests = {
71017095 message :
71027096 "React Hook useEffect has a missing dependency: 'local'. " +
71037097 'Either include it or remove the dependency array.' ,
7098+ suggestions : [
7099+ {
7100+ desc : 'Update the dependencies array to be: [local]' ,
7101+ output : normalizeIndent `
7102+ function MyComponent() {
7103+ const local = {};
7104+ useEffect(() => {
7105+ console.log(local);
7106+ }, [local]);
7107+ }
7108+ ` ,
7109+ } ,
7110+ ] ,
71047111 } ,
71057112 ] ,
71067113 // Keep this until major IDEs and VS Code FB ESLint plugin support Suggestions API.
@@ -8217,30 +8224,45 @@ if (!process.env.CI) {
82178224 testsTypescript . invalid = testsTypescript . invalid . filter ( predicate ) ;
82188225}
82198226
8220- describe ( 'react- hooks' , ( ) => {
8221- const parserOptions = {
8227+ describe ( 'rules-of- hooks/exhaustive-deps ' , ( ) => {
8228+ const parserOptionsV7 = {
82228229 ecmaFeatures : {
82238230 jsx : true ,
82248231 } ,
82258232 ecmaVersion : 6 ,
82268233 sourceType : 'module' ,
82278234 } ;
8235+ const languageOptionsV9 = {
8236+ ecmaVersion : 6 ,
8237+ sourceType : 'module' ,
8238+ parserOptions : {
8239+ ecmaFeatures : {
8240+ jsx : true ,
8241+ } ,
8242+ } ,
8243+ } ;
82288244
82298245 const testsBabelEslint = {
82308246 valid : [ ...testsFlow . valid , ...tests . valid ] ,
82318247 invalid : [ ...testsFlow . invalid , ...tests . invalid ] ,
82328248 } ;
82338249
8234- new ESLintTester ( {
8250+ new ESLintTesterV7 ( {
82358251 parser : require . resolve ( 'babel-eslint' ) ,
8236- parserOptions,
8237- } ) . run ( 'parser: babel-eslint' , ReactHooksESLintRule , testsBabelEslint ) ;
8252+ parserOptions : parserOptionsV7 ,
8253+ } ) . run (
8254+ 'eslint: v7, parser: babel-eslint' ,
8255+ ReactHooksESLintRule ,
8256+ testsBabelEslint
8257+ ) ;
82388258
8239- new ESLintTester ( {
8240- parser : require . resolve ( '@babel/eslint-parser' ) ,
8241- parserOptions,
8259+ new ESLintTesterV9 ( {
8260+ languageOptions : {
8261+ ...languageOptionsV9 ,
8262+ parser : require ( '@babel/eslint-parser' ) ,
8263+ } ,
82428264 } ) . run (
8243- 'parser: @babel/eslint-parser' ,
8265+ 'eslint: v9, parser: @babel/eslint-parser' ,
82448266 ReactHooksESLintRule ,
82458267 testsBabelEslint
82468268 ) ;
@@ -8250,49 +8272,119 @@ describe('react-hooks', () => {
82508272 invalid : [ ...testsTypescript . invalid , ...tests . invalid ] ,
82518273 } ;
82528274
8253- new ESLintTester ( {
8275+ new ESLintTesterV7 ( {
82548276 parser : require . resolve ( '@typescript-eslint/parser-v2' ) ,
8255- parserOptions,
8277+ parserOptions : parserOptionsV7 ,
8278+ } ) . run (
8279+ 'eslint: v7, parser: @typescript-eslint/[email protected] ' , 8280+ ReactHooksESLintRule ,
8281+ testsTypescriptEslintParser
8282+ ) ;
8283+
8284+ new ESLintTesterV9 ( {
8285+ languageOptions : {
8286+ ...languageOptionsV9 ,
8287+ parser : require ( '@typescript-eslint/parser-v2' ) ,
8288+ } ,
82568289 } ) . run (
8257- 'parser: @typescript-eslint/[email protected] ' , 8290+ 'eslint: v9, parser: @typescript-eslint/[email protected] ' , 82588291 ReactHooksESLintRule ,
82598292 testsTypescriptEslintParser
82608293 ) ;
82618294
8262- new ESLintTester ( {
8295+ new ESLintTesterV7 ( {
82638296 parser : require . resolve ( '@typescript-eslint/parser-v3' ) ,
8264- parserOptions,
8297+ parserOptions : parserOptionsV7 ,
82658298 } ) . run (
8266- 'parser: @typescript-eslint/[email protected] ' , 8299+ 'eslint: v7, parser: @typescript-eslint/[email protected] ' , 82678300 ReactHooksESLintRule ,
82688301 testsTypescriptEslintParser
82698302 ) ;
82708303
8271- new ESLintTester ( {
8304+ new ESLintTesterV9 ( {
8305+ languageOptions : {
8306+ ...languageOptionsV9 ,
8307+ parser : require ( '@typescript-eslint/parser-v3' ) ,
8308+ } ,
8309+ } ) . run (
8310+ 'eslint: v9, parser: @typescript-eslint/[email protected] ' , 8311+ ReactHooksESLintRule ,
8312+ testsTypescriptEslintParser
8313+ ) ;
8314+
8315+ new ESLintTesterV7 ( {
82728316 parser : require . resolve ( '@typescript-eslint/parser-v4' ) ,
8273- parserOptions,
8274- } ) . run ( 'parser: @typescript-eslint/[email protected] ' , ReactHooksESLintRule , { 8275- valid : [
8276- ...testsTypescriptEslintParserV4 . valid ,
8277- ...testsTypescriptEslintParser . valid ,
8278- ] ,
8279- invalid : [
8280- ...testsTypescriptEslintParserV4 . invalid ,
8281- ...testsTypescriptEslintParser . invalid ,
8282- ] ,
8283- } ) ;
8317+ parserOptions : parserOptionsV7 ,
8318+ } ) . run (
8319+ 'eslint: v7, parser: @typescript-eslint/[email protected] ' , 8320+ ReactHooksESLintRule ,
8321+ {
8322+ valid : [
8323+ ...testsTypescriptEslintParserV4 . valid ,
8324+ ...testsTypescriptEslintParser . valid ,
8325+ ] ,
8326+ invalid : [
8327+ ...testsTypescriptEslintParserV4 . invalid ,
8328+ ...testsTypescriptEslintParser . invalid ,
8329+ ] ,
8330+ }
8331+ ) ;
82848332
8285- new ESLintTester ( {
8333+ new ESLintTesterV9 ( {
8334+ languageOptions : {
8335+ ...languageOptionsV9 ,
8336+ parser : require ( '@typescript-eslint/parser-v4' ) ,
8337+ } ,
8338+ } ) . run (
8339+ 'eslint: v9, parser: @typescript-eslint/[email protected] ' , 8340+ ReactHooksESLintRule ,
8341+ {
8342+ valid : [
8343+ ...testsTypescriptEslintParserV4 . valid ,
8344+ ...testsTypescriptEslintParser . valid ,
8345+ ] ,
8346+ invalid : [
8347+ ...testsTypescriptEslintParserV4 . invalid ,
8348+ ...testsTypescriptEslintParser . invalid ,
8349+ ] ,
8350+ }
8351+ ) ;
8352+
8353+ new ESLintTesterV7 ( {
82868354 parser : require . resolve ( '@typescript-eslint/parser-v5' ) ,
8287- parserOptions,
8288- } ) . run ( 'parser: @typescript-eslint/parser@^5.0.0-0' , ReactHooksESLintRule , {
8289- valid : [
8290- ...testsTypescriptEslintParserV4 . valid ,
8291- ...testsTypescriptEslintParser . valid ,
8292- ] ,
8293- invalid : [
8294- ...testsTypescriptEslintParserV4 . invalid ,
8295- ...testsTypescriptEslintParser . invalid ,
8296- ] ,
8297- } ) ;
8355+ parserOptions : parserOptionsV7 ,
8356+ } ) . run (
8357+ 'eslint: v7, parser: @typescript-eslint/parser@^5.0.0-0' ,
8358+ ReactHooksESLintRule ,
8359+ {
8360+ valid : [
8361+ ...testsTypescriptEslintParserV4 . valid ,
8362+ ...testsTypescriptEslintParser . valid ,
8363+ ] ,
8364+ invalid : [
8365+ ...testsTypescriptEslintParserV4 . invalid ,
8366+ ...testsTypescriptEslintParser . invalid ,
8367+ ] ,
8368+ }
8369+ ) ;
8370+
8371+ new ESLintTesterV9 ( {
8372+ languageOptions : {
8373+ ...languageOptionsV9 ,
8374+ parser : require ( '@typescript-eslint/parser-v5' ) ,
8375+ } ,
8376+ } ) . run (
8377+ 'eslint: v9, parser: @typescript-eslint/parser@^5.0.0-0' ,
8378+ ReactHooksESLintRule ,
8379+ {
8380+ valid : [
8381+ ...testsTypescriptEslintParserV4 . valid ,
8382+ ...testsTypescriptEslintParser . valid ,
8383+ ] ,
8384+ invalid : [
8385+ ...testsTypescriptEslintParserV4 . invalid ,
8386+ ...testsTypescriptEslintParser . invalid ,
8387+ ] ,
8388+ }
8389+ ) ;
82988390} ) ;
0 commit comments