-
-
Notifications
You must be signed in to change notification settings - Fork 86
feat: Allow rules to specify languages they work on #135
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Changes from all commits
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
e38a39f
feat: Allow rules to specify languages they work on
nzakas 130e0e7
Apply feedback
nzakas 57fa2ce
Mention * pattern for languages
nzakas 8580423
Throw an error when rule language doesn't match
nzakas f89a9e2
Update designs/2025-rule-languages/README.md
nzakas 6133bae
Update designs/2025-rule-languages/README.md
nzakas File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,121 @@ | ||||||||||||
| - Repo: eslint/eslint | ||||||||||||
| - Start Date: 2025-06-11 | ||||||||||||
| - RFC PR: https://github.com/eslint/rfcs/pull/135 | ||||||||||||
| - Authors: Nicholas C. Zakas | ||||||||||||
|
|
||||||||||||
| # Allow rules to specify the languages/dialects they work on | ||||||||||||
|
|
||||||||||||
| ## Summary | ||||||||||||
|
|
||||||||||||
| This RFC proposes adding metadata to ESLint rules that indicate which programming languages and language dialects they support. This will enable better documentation and runtime capabilities for ESLint when working with multiple languages. | ||||||||||||
|
|
||||||||||||
| ## Motivation | ||||||||||||
|
|
||||||||||||
| Currently, an ESLint rule has no way to indicate which languages or language dialects it is designed to work with. This limitation creates two significant problems: | ||||||||||||
|
|
||||||||||||
| 1. **Documentation purposes** - Users have no easy way to determine which JavaScript rules have been updated to support TypeScript syntax, for example. This makes it harder to understand which rules can be safely enabled when linting TypeScript code. | ||||||||||||
|
|
||||||||||||
| 2. **Runtime purposes** - Currently, rules that don't apply to a given language crash in unpredictable ways, causing confusion for users. Ideally, ESLint would throw an error with a descriptive message stating that these rules cannot be used with the given language. | ||||||||||||
|
|
||||||||||||
| As ESLint's ecosystem expands to support more languages beyond JavaScript (such as TypeScript, CSS, and potentially others), having a standardized way to specify language compatibility becomes increasingly important for both users and maintainers. | ||||||||||||
|
|
||||||||||||
| ## Detailed Design | ||||||||||||
|
|
||||||||||||
| I propose adding a `languages` array to the rule's `meta` object. Example: | ||||||||||||
|
|
||||||||||||
| ```js | ||||||||||||
| // Rule definition example | ||||||||||||
| module.exports = { | ||||||||||||
| meta: { | ||||||||||||
| type: "suggestion", | ||||||||||||
| docs: { | ||||||||||||
| description: "Disallow something", | ||||||||||||
| recommended: true | ||||||||||||
| }, | ||||||||||||
|
|
||||||||||||
| // new property | ||||||||||||
| languages: ["markdown/gfm", "markdown/commonmark"] // Languages the rule supports | ||||||||||||
| }, | ||||||||||||
| create(context) { | ||||||||||||
| // Rule implementation | ||||||||||||
| return {}; | ||||||||||||
| } | ||||||||||||
| }; | ||||||||||||
| ``` | ||||||||||||
|
|
||||||||||||
| The `languages` array will contain strings that identify the specific language plugins the rule is designed to work with. Each string follows the standardized format `"plugin/language"` to uniquely identify the language plugin. Special syntax: | ||||||||||||
|
|
||||||||||||
| - To specify that a rule works with any language in a plugin, the format of `"plugin/*"` is used. | ||||||||||||
| - To specify that a rule works for any language, `"*"` is used. | ||||||||||||
|
|
||||||||||||
| For backward compatibility, if `languages` is not specified, the rule will be assumed to work with all languages. (Effectively, the same as `languages: ["*"]`). | ||||||||||||
|
|
||||||||||||
| For rules meant to work only with JavaScript, the `"js/js"` string is used. In the short-term, we'll need to special case this to match `"@/js"`, which is how the JavaScript language is defined right now. In the long-term, once `@eslint/js` fully contains the language, we can remove the check. | ||||||||||||
|
|
||||||||||||
| ### Implementation Approach | ||||||||||||
|
|
||||||||||||
| 1. Update the `RuleMeta` interface in `@eslint/core` to accept `languages`. Deprecate the `language` and `dialects` properties. Add `meta.docs.dialects` property. | ||||||||||||
| 2. Update the `validateRulesConfig()` function in `lib/config/config.js` to validate each rule's `languages` property against the language specified in the `Config` instance. When a rule doesn't match the language, add to an array of invalid rules. When all validation is complete, if there is an array of invalid rules, throw an error. Normalize `"js/js"` to `"@/js"`. | ||||||||||||
|
||||||||||||
| 2. Update the `validateRulesConfig()` function in `lib/config/config.js` to validate each rule's `languages` property against the language specified in the `Config` instance. When a rule doesn't match the language, add to an array of invalid rules. When all validation is complete, if there is an array of invalid rules, throw an error. Normalize `"js/js"` to `"@/js"`. | |
| 2. Update the `validateRulesConfig()` function in `lib/config/config.js`: | |
| - **Validation Logic**: Validate each rule's `languages` property against the language specified in the `Config` instance. If a rule's `languages` property does not match the specified language, mark it as invalid by adding it to an array of invalid rules. | |
| - **Error Handling**: After completing the validation for all rules, check if there are any invalid rules in the array. If so, throw an error with a descriptive message listing the invalid rules. | |
| - **Normalization**: Normalize the `"js/js"` string to `"@/js"` to ensure compatibility with the current JavaScript language definition. |
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The implementation step mentions adding
meta.docs.dialectsproperty but this property is not explained elsewhere in the RFC. Consider clarifying what this property is for and how it relates to thelanguagesarray, or remove it if it's not needed.Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The suggested change is bogus. As for "Consider clarifying what this property is for", that makes sense, although it's explained in the related discussion in eslint/eslint#19462, and I'm not sure if Copilot bothered reading that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think Copilot works great in documentation situations. I've found it often misses a lot of context.