Skip to content

Commit

Permalink
[Perf] component detection: improve performance by avoiding traversin…
Browse files Browse the repository at this point in the history
…g parents unnecessarily (jsx-eslint#3459)
  • Loading branch information
golopot authored and ljharb committed Oct 11, 2022
1 parent 4360fa3 commit c8159fc
Show file tree
Hide file tree
Showing 3 changed files with 24 additions and 22 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Expand Up @@ -5,6 +5,11 @@ This change log adheres to standards from [Keep a CHANGELOG](https://keepachange

## Unreleased

### Changed
* [Perf] component detection: improve performance by avoiding traversing parents unnecessarily ([#3459][] @golopot)

[#3459]: https://github.com/jsx-eslint/eslint-plugin-react/pull/3459

## [7.31.10] - 2022.10.10

### Fixed
Expand Down
39 changes: 18 additions & 21 deletions lib/util/Components.js
Expand Up @@ -109,7 +109,7 @@ class Components {
set(node, props) {
const list = Lists.get(this);
let component = list[getId(node)];
while (!component) {
while (!component || component.confidence < 1) {
node = node.parent;
if (!node) {
return;
Expand Down Expand Up @@ -477,7 +477,6 @@ function componentRule(rule, context) {
}

if (node.type === 'FunctionExpression' || node.type === 'ArrowFunctionExpression') {
const isMethod = parent.type === 'Property' && parent.method;
const isPropertyAssignment = parent.type === 'AssignmentExpression'
&& parent.left.type === 'MemberExpression';
const isModuleExportsAssignment = isPropertyAssignment
Expand Down Expand Up @@ -562,6 +561,18 @@ function componentRule(rule, context) {
return undefined;
}

if (
node.parent.type === 'Property' && (
(node.parent.method && !node.parent.computed) // case: { f() { return ... } }
|| (!node.id && !node.parent.computed) // case: { f: () => ... }
)
) {
if (isFirstLetterCapitalized(node.parent.key.name) && utils.isReturningJSX(node)) {
return node;
}
return undefined;
}

// Case like `React.memo(() => <></>)` or `React.forwardRef(...)`
const pragmaComponentWrapper = utils.getPragmaComponentWrapper(node);
if (pragmaComponentWrapper && utils.isReturningJSXOrNull(node)) {
Expand All @@ -576,10 +587,6 @@ function componentRule(rule, context) {
return undefined;
}

if (isMethod && !isFirstLetterCapitalized(node.parent.key.name)) {
return utils.isReturningJSX(node) ? node : undefined;
}

if (node.id) {
return isFirstLetterCapitalized(node.id.name) ? node : undefined;
}
Expand Down Expand Up @@ -853,13 +860,8 @@ function componentRule(rule, context) {
return;
}

const component = utils.getParentComponent();
if (
!component
|| (component.parent && component.parent.type === 'JSXExpressionContainer')
) {
// Ban the node if we cannot find a parent component
components.add(node, 0);
const component = utils.getStatelessComponent(node);
if (!component) {
return;
}
components.add(component, 2);
Expand All @@ -871,7 +873,7 @@ function componentRule(rule, context) {
return;
}

node = utils.getParentComponent();
node = utils.getStatelessComponent(node);
if (!node) {
return;
}
Expand All @@ -884,13 +886,8 @@ function componentRule(rule, context) {
return;
}

const component = utils.getParentComponent();
if (
!component
|| (component.parent && component.parent.type === 'JSXExpressionContainer')
) {
// Ban the node if we cannot find a parent component
components.add(node, 0);
const component = utils.getStatelessComponent(node);
if (!component) {
return;
}
components.add(component, 2);
Expand Down
2 changes: 1 addition & 1 deletion tests/lib/rules/destructuring-assignment.js
Expand Up @@ -459,7 +459,7 @@ ruleTester.run('destructuring-assignment', rule, {
},
{
code: `
var Hello = React.createClass({
var Hello = createReactClass({
render: function() {
return <Text>{this.props.foo}</Text>;
}
Expand Down

0 comments on commit c8159fc

Please sign in to comment.