feat: Add getPossibleTypesForSelectorClass to Language interface#148
feat: Add getPossibleTypesForSelectorClass to Language interface#148Kuldeep2822k wants to merge 7 commits into
Conversation
|
Hi @Kuldeep2822k!, thanks for the Pull Request The pull request title isn't properly formatted. We ask that you update the pull request title to match this format, as we use it to generate changelogs and automate releases.
To Fix: You can fix this problem by clicking 'Edit' next to the pull request title at the top of this page. Read more about contributing to ESLint here |
|
|
||
| ## Help Needed | ||
|
|
||
| I am willing to submit a pull request with the reference implementation for this RFC once it is accepted. Performance benchmarking (using `npm run test:performance`) will be done to confirm there is no regression. |
There was a problem hiding this comment.
I tested the performance with and without the current switch case for "class" in analyzeParsedSelector using npm run test:performance. There was no difference as no core rule uses the :function selector, so we would need another benchmark for this.
There was a problem hiding this comment.
You're right — no core rule uses :function, so test:performance can't exercise this path. I've dropped that reference from the RFC. The architectural framing (delegating static-analysis ownership to the language plugin) was always the primary motivation here .
| fallback: vk.getKeys, | ||
| matchClass: this.#language.matchesSelectorClass ?? (() => false), | ||
| nodeTypeKey: this.#language.nodeTypeKey, | ||
| + language: this.#language, |
There was a problem hiding this comment.
The other properties and methods from this.#language are passed directly, so why pass the whole language instead of only getPossibleTypesForSelectorClass?
There was a problem hiding this comment.
Good point, you're right. I'll switch to passing only the method.
The reason I had it as the full language was the cache — it's currently a WeakMap keyed by language object. Since the JS language exports a singleton and getSelectorClassNodeTypes is a stable reference, I can key the cache on the method instead and keep the pattern consistent:
js getSelectorClassNodeTypes: this.#language.getSelectorClassNodeTypes,
Pushing an update shortl
| const noLanguageCache = new Map(); | ||
|
|
||
| function getLanguageCache(language) { | ||
| if (!language) { |
There was a problem hiding this comment.
The language is always set, so there is no need for noLanguageCache.
| - ]; | ||
| - } | ||
| - return null; | ||
| + return language?.getPossibleTypesForSelectorClass?.(selector.name) ?? null; |
There was a problem hiding this comment.
| + return language?.getPossibleTypesForSelectorClass?.(selector.name) ?? null; | |
| + return language.getPossibleTypesForSelectorClass?.(selector.name) ?? null; |
The language cannot be nullish.
Summary
Add an optional getPossibleTypesForSelectorClass(className) method to the Language interface that allows languages to declare which AST node types could match a given pseudo-class selector (e.g., :function). This removes hardcoded JavaScript-specific logic from the core selector analysis in lib/linter/esquery.js and enables any language plugin to provide the same optimization.
Related Issues
matchesSelectorClass()