Skip to content

fix(eslint-plugin-query): only match own properties in no-unstable-deps - #11180

Open
yogesh968 wants to merge 1 commit into
TanStack:mainfrom
yogesh968:fix/eslint-no-unstable-deps-own-property
Open

fix(eslint-plugin-query): only match own properties in no-unstable-deps#11180
yogesh968 wants to merge 1 commit into
TanStack:mainfrom
yogesh968:fix/eslint-no-unstable-deps-own-property

Conversation

@yogesh968

@yogesh968 yogesh968 commented Aug 13, 2026

Copy link
Copy Markdown

Fixes #11118

The problem

no-unstable-deps keeps three plain objects keyed by identifier name, and reads all three without checking that the key is an own property:

// hook aliases
if (reactHookNames.includes(calleeName) || calleeName in hookAliasMap)

// tracked custom hooks
return trackedCustomHooks[callExpression.callee.name]

// tracked variables
if (dep.type === AST_NODE_TYPES.Identifier && trackedVariables[dep.name] !== undefined)

Names inherited from Object.prototype therefore resolve to a prototype member instead of undefined, and unrelated code gets reported. #11118 covers the trackedCustomHooks lookup. The other two produce their own false positives:

  • a dependency named toString, constructor or valueOf is reported as the result of a query hook, with the inherited function interpolated into the message
  • a call such as constructor(fn, [query]) is treated as a React hook invocation, and its second argument is checked as a dependency array

The toString case is the one from the issue's StackBlitz, where toString comes from Lodash.

The change

Guard all three lookups with Object.hasOwn, which is what the issue suggests.

Tests

Three cases added to no-unstable-deps.test.ts, one per lookup. All three fail on main and pass here. Rule suite is green: 246 tests.

Note

There are two open PRs on this issue, #11117 and #11125, and both fix the trackedCustomHooks lookup only. I ran into the other two lookups while checking whether that was the whole story, so this covers all three. Happy to rebase on either of them, or to close this if you would rather take one of those and have the remaining two handled as a follow up.

Summary by CodeRabbit

  • Bug Fixes

    • Fixed no-unstable-deps incorrectly recognizing inherited names such as toString and constructor as React hooks, custom hooks, or tracked dependencies.
    • Improved dependency analysis to only recognize explicitly tracked identifiers.
  • Tests

    • Added regression coverage for identifiers that conflict with inherited object properties.

The rule keeps three plain objects keyed by identifier name: tracked
custom hooks, tracked variables and React hook aliases. All three were
read with a bare index access or the 'in' operator, so names inherited
from 'Object.prototype' resolved to a prototype member instead of
'undefined'.

Code using an identifier called 'toString', 'constructor' or 'valueOf'
was therefore treated as a tracked query hook. A dependency named
'toString' got reported, and a call such as 'constructor(fn, [query])'
was treated as a React hook invocation.

Guard the three lookups with 'Object.hasOwn'.
@coderabbitai

coderabbitai Bot commented Aug 13, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: c000feeb-828a-46b8-92e0-5fba4f590603

📥 Commits

Reviewing files that changed from the base of the PR and between 159982c and a46691a.

📒 Files selected for processing (3)
  • .changeset/lucky-eels-count.md
  • packages/eslint-plugin-query/src/__tests__/no-unstable-deps.test.ts
  • packages/eslint-plugin-query/src/rules/no-unstable-deps/no-unstable-deps.rule.ts

📝 Walkthrough

Walkthrough

The no-unstable-deps rule now ignores inherited Object.prototype properties during identifier tracking. Regression tests cover names such as toString, constructor, and valueOf. A patch changeset documents the fix.

Changes

no-unstable-deps identifier tracking

Layer / File(s) Summary
Restrict identifier tracking to own properties
packages/eslint-plugin-query/src/rules/no-unstable-deps/no-unstable-deps.rule.ts
Hook aliases, custom hooks, and tracked dependencies now use Object.hasOwn.
Add regression coverage and release note
packages/eslint-plugin-query/src/__tests__/no-unstable-deps.test.ts, .changeset/lucky-eels-count.md
Valid cases cover inherited Object.prototype names. A patch changeset documents the correction.

Estimated code review effort: 2 (Simple) | ~10 minutes

Mergeability Score: ⚪ Minimal · up to a4669

This localized change prevents prototype-inherited names from being treated as configured hooks or variables, with no actionable merge-blocking risk remaining after normal checks and review.

Possibly related PRs

  • TanStack/query#11117: Both changes add own-property checks and regression tests for no-unstable-deps.
  • TanStack/query#11125: Both changes prevent inherited names such as toString from causing false positives.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly identifies the main change: restricting no-unstable-deps matches to own properties.
Description check ✅ Passed The description clearly explains the problem, implementation, regression tests, and release impact.
Linked Issues check ✅ Passed The changes satisfy issue #11118 and also address the same prototype-lookup bug in two related rule lookups.
Out of Scope Changes check ✅ Passed The additional alias and variable checks address the same root cause and remain within the linked issue's scope.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

eslint-plugin-query: no-unstable-deps incorrectly treats inherited Object.prototype properties as tracked custom hooks

2 participants