Skip to content

add eslint-import-resolver-typescript as a dependency #150

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

Closed
Zamiell opened this issue Sep 7, 2024 · 21 comments
Closed

add eslint-import-resolver-typescript as a dependency #150

Zamiell opened this issue Sep 7, 2024 · 21 comments

Comments

@Zamiell
Copy link
Contributor

Zamiell commented Sep 7, 2024

From @silverwind:

I think eslint-import-resolver-typescript is currently only mandatory for typescript, but I think we should make it a dependency and default to it for both JS and TS. The default JS resolver has too many issues like not supporting exports object format which are resolved in the typescript resolver.

(Originally in this pull request.)

Doing this would simplify the config for the end-user, which would be a big win!

cc @SukkaW @michaelfaith

@SukkaW
Copy link
Collaborator

SukkaW commented Sep 7, 2024

There are still a few serious issues with eslint-import-resolver-typescript.

Also I am putting my bet on https://github.com/9romise/eslint-import-resolver-oxc as well.

@Zamiell Zamiell changed the title feat: add eslint-import-resolver-typescript as a dependency add eslint-import-resolver-typescript as a dependency Sep 7, 2024
@michaelfaith
Copy link
Contributor

Thougts about absorbing typescript parser into the typescript flat config, too? That'd add an optional peer dependency on @typescript-eslint/parser, but remove the need for users to have to define a parser.

@SukkaW
Copy link
Collaborator

SukkaW commented Sep 8, 2024

That'd add an optional peer dependency

I don't know how the package managers would handle this. It seems that yarn 1, yarn@berry, npm@5, npm@latest, pnpm@6, and pnpm@latest all handle optional peer dependencies differently.

Also, since most package managers don't hoist the transitive dependencies.

@michaelfaith
Copy link
Contributor

michaelfaith commented Sep 9, 2024

That'd add an optional peer dependency

I don't know how the package managers would handle this. It seems that yarn 1, yarn@berry, npm@5, npm@latest, pnpm@6, and pnpm@latest all handle optional peer dependencies differently.

Also, since most package managers don't hoist the transitive dependencies.

Not sure I follow. All three package managers support peerDependenciesMeta.optional (yarn 1 & berry, npm since v7 / node 15, and pnpm). It wouldn't be a transitive dependency though. The consuming project would still need to have it installed as a first class dep, if they're using the typescript config.
(optional peer dependency, not optional dependency)

@SukkaW
Copy link
Collaborator

SukkaW commented Sep 10, 2024

It wouldn't be a transitive dependency though.

What happens if someone is publishing his eslint presets to npm (e.g. @antfu/eslint-config and eslint-config-sukka)? Then eslint-import-resolver-typescript becomes a transitive dependency of that preset package. Even if eslint-import-resolver-typescript is listed as a direct dependency of that preset package, it is still a transitive dependency (current project -> eslint-config-presets => eslint-import-resolver-typescript).

This used to cause me shit loads of issues when I am building eslint-config-sukka.

@Zamiell
Copy link
Contributor Author

Zamiell commented Sep 10, 2024

It wouldn't be a transitive dependency though.

What happens if someone is publishing his eslint presets to npm (e.g. @antfu/eslint-config and eslint-config-sukka)? Then eslint-import-resolver-typescript becomes a transitive dependency of that preset package. Even if eslint-import-resolver-typescript is listed as a direct dependency of that preset package, it is still a transitive dependency (current project -> eslint-config-presets => eslint-import-resolver-typescript).

This used to cause me shit loads of issues when I am building eslint-config-sukka.

I tried this over the weekend, and with the npm package manager specifically, it won't work properly if the dependency chain is like:

my-project --> my-linting-metapackage --> eslint-config-foo --> eslint-plugin-import-x & eslint-import-resolver-typescript

However, the dependency chain DOES work just fine if the dependency chain is like:

my-project --> my-linting-metapackage --> eslint-config-foo & eslint-import-resolver-typescript

I didn't test any other package managers than npm.

Thus, I think there is still value in putting eslint-import-resolver-typescript as a direct dependency of eslint-plugin-import-x, since some people (or maybe most people? unsure) will not consume eslint-import-plugin-x through a linting metapackage that nests the eslint-import-resolver-typescript dep more than two layers deep, if that makes sense. (And you could add this limitation to the readme.)

@error-four-o-four
Copy link
Contributor

error-four-o-four commented Sep 10, 2024

Hey there,

I was wondering if it would make sense to add support for (conditional) exports fields in package json files to the (default) node resolver instead of introducing another dependency?

imho the only purpose of eslint-import-resolver-typescript should be to resolve .ts, .d.ts files, aliased and project paths

@silverwind
Copy link
Contributor

silverwind commented Sep 10, 2024

I was wondering if it would make sense to add support for (conditional) exports fields in package json files to the (default) node resolver instead of introducing another dependency?

It would, but the counter-argument is that maintaining two resolvers will not go well in the long run and it's better to focus efforts on making one resolver good for everything, even at the cost of additional dependencies, which are often not much of a cost to bear.

@error-four-o-four
Copy link
Contributor

error-four-o-four commented Sep 10, 2024

Please let me know if this is unrelated or not the right place (as there also is #40) or if I'm wrong.
eslint-import-resolver-node (and others) rely on resolve whereas eslint-import-resolver-typescript introduces enhanced-resolve. In my case (and I don't know if it's an edge case) I'm pretty sure that I won't be using webpack in any of my projects in the near future. Therefore I'm not enthusiastic about this package, but that's just an opinion. I didn't take a closer look at these packages regarding performance or benchmark but I'm sure that their doing a great job.
Anyway your point is absolutely reasonable.
The way I see it is, that it would be great to have some kind of extendable resolver. Like a monorepo with a 'core' package. Other resolver packages/workspaces (like ts, webpack, vue, whatever) could extend this core package and wouldn't have to rewrite/build core functionality again.

@vladshcherbin
Copy link

vladshcherbin commented Dec 2, 2024

Something should be done with the default resolver, which is not aware of exports definition in package.json import-js/eslint-plugin-import#1810 - more and more packages give incorrect error warnings e.g. eslint-plugin-perfectionist, typescript-eslint

To say at least, I'd absolutely love seeing a huge warning notice about this limitation and discouragement of using default resolver, would save so much time and head scratching

image

@SukkaW
Copy link
Collaborator

SukkaW commented Dec 2, 2024

To say at least, I'd absolutely love seeing a huge warning notice about this limitation and discouragement of using default resolver, would save so much time and head scratching

That's right. The default built-in resolver is an outdated resolver eslint-import-resolver-node and is based on the package resolve. It is so old that it doesn't support exports in the package.json.

In the next major version, we will remove eslint-import-resolver-node and make it an opt-in one. People can switch to any eslint-import-resolver they like!

@oleksandr-danylchenko
Copy link

Hello, @SukkaW 👋🏻
Any news on when could we expect the version where the resolver with the exports support will become a default?

@SukkaW
Copy link
Collaborator

SukkaW commented Mar 6, 2025

Hello, @SukkaW 👋🏻 Any news on when could we expect the version where the resolver with the exports support will become a default?

In the next major version, the built-in node resolver (that supports exports! Yes it has already been implemented, see #208) will become the default resolver.

In the meantime, you will still need to manually import and use that in your eslint.config.js.

@JounQin
Copy link
Member

JounQin commented Mar 6, 2025

Why not use import.meta.resolve for the node resolver? Is it because it's synchronous only?

Yes. The resolving happens inside the ESLint plugin, and the ESLint plugin needs to be synchronous. Besides import.meta.resolve only exists in ESM while both eslint-plugin-import-x and eslint-plugin-import have many users working with CJS.

@SukkaW See also https://www.npmjs.com/package/@dual-bundle/import-meta-resolve

@SukkaW
Copy link
Collaborator

SukkaW commented Mar 6, 2025

Why not use import.meta.resolve for the node resolver? Is it because it's synchronous only?

Yes. The resolving happens inside the ESLint plugin, and the ESLint plugin needs to be synchronous. Besides import.meta.resolve only exists in ESM while both eslint-plugin-import-x and eslint-plugin-import have many users working with CJS.

@SukkaW See also https://www.npmjs.com/package/@dual-bundle/import-meta-resolve

import.meta.resolve doesn't work well with CJS-only modules since the import-meta-resolve package strictly implements the ESM resolving algorithm, while the ESM resolving algorithm misses a few crucial steps for CJS resolving.

Dropping CJS-only modules support would be a breaking change we might not want to introduce.

@JounQin
Copy link
Member

JounQin commented Mar 6, 2025

import.meta.resolve doesn't work well with CJS-only modules since the import-meta-resolve package strictly implements the ESM resolving algorithm, while the ESM resolving algorithm misses a few crucial steps for CJS resolving.

@SukkaW Can you elaborate what's the issue here for resolving CJS-only modules?

import {resolve} from 'import-meta-resolve'

// A file:
console.log(resolve('./index.js', import.meta.url))
//=> file:///Users/tilde/Projects/oss/import-meta-resolve/index.js

// A CJS package:
console.log(resolve('builtins', import.meta.url))
//=> file:///Users/tilde/Projects/oss/import-meta-resolve/node_modules/builtins/index.js

// A scoped CJS package:
console.log(resolve('@eslint/eslintrc', import.meta.url))
//=> file:///Users/tilde/Projects/oss/import-meta-resolve/node_modules/@eslint/eslintrc/lib/index.js

// A package with an export map:
console.log(resolve('micromark/lib/parse', import.meta.url))
//=> file:///Users/tilde/Projects/oss/import-meta-resolve/node_modules/micromark/lib/parse.js

// A node builtin:
console.log(resolve('fs', import.meta.url))
//=> node:fs

@SukkaW
Copy link
Collaborator

SukkaW commented Mar 6, 2025

import.meta.resolve doesn't work well with CJS-only modules since the import-meta-resolve package strictly implements the ESM resolving algorithm, while the ESM resolving algorithm misses a few crucial steps for CJS resolving.

@SukkaW Can you elaborate what's the issue here for resolving CJS-only modules?

Check out the test case I introduced in https://github.com/un-ts/eslint-plugin-import-x/pull/209/files#diff-8f1ca7dc1831cb622e7f670ebf6b8bf8fe0ce43bd506ae9a11c93b90491ea6d5. Actually I have already tried @dual-bundle/import-meta-resolve when implementing #209, turns out that it can't pass the test cases, so I switch to enhanced-resolve instead.

@JounQin
Copy link
Member

JounQin commented Mar 6, 2025

Check out the test case I introduced in https://github.com/un-ts/eslint-plugin-import-x/pull/209/files#diff-8f1ca7dc1831cb622e7f670ebf6b8bf8fe0ce43bd506ae9a11c93b90491ea6d5. Actually I have already tried @dual-bundle/import-meta-resolve when implementing #209, turns out that it can't pass the test cases, so I switch to enhanced-resolve instead.

Thanks, I'll take a look when I'm free.

@JounQin
Copy link
Member

JounQin commented Mar 20, 2025

Considering --experimental-strip-types, we'll need to add built-in TypeScript support in the future.

@JounQin
Copy link
Member

JounQin commented Mar 20, 2025

By the way, eslint-import-resolver-typescript is now also powered by rspack-resolver unrs-resolver which has P'n'P support correctly.

So actually you don't need eslint-import-resolver-oxc any longer.

@JounQin
Copy link
Member

JounQin commented Jun 5, 2025

Close in favor of #272

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

No branches or pull requests

8 participants