React: Bug: Cannot read property 'references' of undefined in eslint-plugin-react-hooks v4.0.5

Created on 2 Jul 2020  路  3Comments  路  Source: facebook/react

Certain code patterns using optional chaining syntax causes eslint-plugin-react-hooks to throw an error.

React version: 16.10.2

Steps To Reproduce

  1. Install eslint-plugin-react-hooks v4.0.5
  2. Put this code in a file:
import React, { useEffect } from 'react';

export const Repro = (props) => {
  const foo = {};

  const bar = () => ({
    pizza: foo.pizza,
    pasta: foo?.pasta,
  });

  useEffect(bar, []);

  return <div />;
};

The current behavior

ESLint throws the following error:

TypeError: Cannot read property 'references' of undefined
Occurred while linting /path/to/repo/file.ts:102
    at /path/to/repo/node_modules/eslint-plugin-react-hooks/cjs/eslint-plugin-react-hooks.development.js:1681:23
    at Set.forEach (<anonymous>)
    at visitFunctionWithDependencies (/path/to/repo/node_modules/eslint-plugin-react-hooks/cjs/eslint-plugin-react-hooks.development.js:1672:29)
    at visitCallExpression (/path/to/repo/node_modules/eslint-plugin-react-hooks/cjs/eslint-plugin-react-hooks.development.js:886:19)
    at /path/to/repo/node_modules/eslint/lib/linter/safe-emitter.js:45:58
    at Array.forEach (<anonymous>)
    at Object.emit (/path/to/repo/node_modules/eslint/lib/linter/safe-emitter.js:45:38)
    at NodeEventGenerator.applySelector (/path/to/repo/node_modules/eslint/lib/linter/node-event-generator.js:254:26)
    at NodeEventGenerator.applySelectors (/path/to/repo/node_modules/eslint/lib/linter/node-event-generator.js:283:22)
    at NodeEventGenerator.enterNode (/path/to/repo/node_modules/eslint/lib/linter/node-event-generator.js:297:14)

The expected behavior

ESLint does not throw an error.

This looks related to https://github.com/facebook/react/issues/19043 and https://github.com/facebook/react/pull/19062.

I've noticed that it does not throw if a number of slight variations are made to the code. The following do not throw:

import React, { useEffect } from 'react';

export const Repro = (props) => {
  const foo = {};

  const bar = {
    pizza: foo.pizza,
    pasta: foo?.pasta,
  };

  useEffect(bar, []);

  return <div />;
};
import React, { useEffect } from 'react';

export const Repro = (props) => {
  const foo = {};

  const bar = () => ({
    pizza: foo?.pizza,
    pasta: foo?.pasta,
  });

  useEffect(bar, []);

  return <div />;
};
import React, { useEffect } from 'react';

export const Repro = (props) => {
  const foo = {};

  const bar = () => ({
    pizza: something.pizza,
    pasta: foo?.pasta,
  });

  useEffect(bar, []);

  return <div />;
};

cc @krailler

ESLint Rules Bug

Most helpful comment

Optional chaining problems should be fixed in [email protected]. If you experience some problem with optional chaining after 4.0.6, please file a new issue. Thanks.

All 3 comments

Thanks for the report. Would you like to look into a fix?

@gaearon I put up a potential fix here: https://github.com/facebook/react/pull/19260

Optional chaining problems should be fixed in [email protected]. If you experience some problem with optional chaining after 4.0.6, please file a new issue. Thanks.

Was this page helpful?
0 / 5 - 0 ratings