Skip to content
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

[consistent-type-imports] restrict report to the specific offending specifier #4915

Open
3 tasks done
Josh-Cena opened this issue May 6, 2022 · 9 comments
Open
3 tasks done
Labels
accepting prs Go ahead, send a pull request that resolves this issue enhancement New feature or request package: eslint-plugin Issues related to @typescript-eslint/eslint-plugin

Comments

@Josh-Cena
Copy link
Member

  • I have tried restarting my IDE and the issue persists.
  • I have updated to the latest version of the packages.
  • I have read the FAQ and my problem is not listed.

Repro

{
  "rules": {
    "@typescript-eslint/consistent-type-imports": "error"
  }
}
import { a, type b } from "c";

type c = a;
type d = b;

playground

Expected Result

The rule only reports the first ImportSpecifier

Actual Result

The rule reports the entire ImportDeclaration, which makes debugging a little harder when the declaration is long.

I'm not using autofix, because #4338 is not there yet.

Additional Info

Versions

package version
@typescript-eslint/eslint-plugin 5.22.0
@typescript-eslint/parser 5.22.0
TypeScript 4,6.2
ESLint 8.14.0
node 18.0.0
@Josh-Cena Josh-Cena added package: eslint-plugin Issues related to @typescript-eslint/eslint-plugin triage Waiting for maintainers to take a look labels May 6, 2022
@Josh-Cena Josh-Cena changed the title [consistent-type-imports] restrict report to the specific offending [consistent-type-imports] restrict report to the specific offending specifier May 6, 2022
@bradzacher bradzacher added enhancement New feature or request accepting prs Go ahead, send a pull request that resolves this issue and removed triage Waiting for maintainers to take a look labels May 6, 2022
@Josh-Cena
Copy link
Member Author

The fifteen levels of indentation in that rule's source makes me want to instantly quit coding every time I look at it

@bradzacher
Copy link
Member

Yeah the fixer is dog ugly logic to implement unfortunately because imports are so damn complex.

Most of the rule logic isn't THAT bad though. It probably needs a pass over it to rewrite it now that it's written and finalised.

@kirkwaiblinger
Copy link
Member

I think that this kind of implies having a separate loc for each reported import, too, for example

import { a, type b, c } from "outside-module";
         ^          ^

type A = a;
type B = b;
type C = c;

This is kinda of problematic, until #8554 is closed (which looks to be very soon!), due to the amount of fixer logic in the rule. With multipass fixes, I think we can just have each symbol report and fix "individually" but still assert that the actual result is correct

@bradzacher
Copy link
Member

TBH idk if we should do individual reporting if there are multiple per import.
The fixer logic is complicated AF and refactoring it to be able to do each specifier in isolation will be 🤮

@Josh-Cena
Copy link
Member Author

I think we definitely should!

@bradzacher
Copy link
Member

bradzacher commented May 2, 2024

@Josh-Cena the issue with multiple report locations is that it creates multiple fixers and those fixers cannot talk to one another - so either they will conflict or they'll do the same thing

For example imagine this

import { a, b, c } from "outside-module";
         ^     ^

If we want to fix this to an inline style it's easy - for sure:

// fix 1
-import { a, b, c } from "outside-module";
+import { type a, b, c } from "outside-module";

// fix 2
-import { a, b, c } from "outside-module";
+import { a, b, type c } from "outside-module";

These fixes are non-overlapping so easy as.
But if you want to fix to a top-level style:

// fix 1
-import { a, b, c } from "outside-module";
+import { b, c } from "outside-module";
+import type { a } from "outside-module";

// fix 2
-import { a, b, c } from "outside-module";
+import { a, b } from "outside-module";
+import type { c } from "outside-module";

Now you have this issue either

  • eslint will see that the fixers add the same line and so it'll reject the second fixer - which will guarantee an extra lint pass to recalculate and apply the second fix, or
  • eslint will see two non-overlapping insertions - causing two import statements to be inserted for the same module

Either way - that's not a great result! A slower lint run or duplicate code. IMO that's not a great trade-off for the end user for what is a relatively minor improvement.

@kirkwaiblinger
Copy link
Member

Has the idea of a non-contiguous loc for a single report been thought about before? That would allow us to get semantically sensible underlines but one fix... Would also make sense for method-signature-style where multiple method declarations, currently flagged separately, get collapsed to 1 by the fix

@bradzacher
Copy link
Member

I don't think it has - it's a pretty fundamental change to how eslint does things.

I think there's huge value in it eg rust's clippy does multi range reports (but only for "related spans", not primary ones) and it's a great way to expose additional info to users.

@Josh-Cena
Copy link
Member Author

Josh-Cena commented May 2, 2024

What about this: we still uphold the principle of "report what will be changed".

  • If we need to split out a separate statement, report the statement as a whole.
    • However, if we are only splitting out one identifier, only report that identifier.
  • If we are changing a few identifiers (inline style), report those identifiers.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
accepting prs Go ahead, send a pull request that resolves this issue enhancement New feature or request package: eslint-plugin Issues related to @typescript-eslint/eslint-plugin
Projects
None yet
Development

No branches or pull requests

3 participants