-
Notifications
You must be signed in to change notification settings - Fork 16
Doesn't resolve index.js files correctly #178
Comments
Sorry for the late reply... missed this notification... anyway, yes this is a bug indeed and it should definitely handle that by default 👍 . |
I ended up writing from scratch and publishing It can resolve index files, custom extensions, etc. One thing I was not expecting was for it to be so fast — |
I got started on a Shimpit PR that fixed most of the problems with index files, but gave up before getting every type of import/export to work. If you're interested, I might be able to share what I had in a draft PR. |
Sure, thanks! |
The strategy is to not attempt to guess the absolute import file paths at the time they are discovered, but to record the import specifiers more faithfully: {
- "location": "test/core/b/b.js",
+ "location": "test/core/b/b",
"name": "test",
"unnamedDefault": true,
} Then later when analysing what exports are unused, search for the files in the list, resolving file extensions and index files in order of preference (it's good to match the Node.js resolution algorithm). Rather than do a fork and draft PR, here are the relevant diffs (minus updated tests and snapshots)… Line 282 in 6486693
const { exports, imports } = this.modules
const unresolved = exports.reduce((acc, item) => {
if (
- imports.filter(element =>
- element.unnamedDefault
+ imports.filter(imprt =>
+ imprt.unnamedDefault
? // Skip the name in the comparison as a default unnamed export
// can be imported with any name.
// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/export
this.deepStrictEqual(
- { location: element.location, unnamedDefault: true },
+ { location: `${imprt.location}.js`, unnamedDefault: true },
{
location: item.location,
unnamedDefault: item.unnamedDefault,
},
)
: // Compare the raw element & item.
- this.deepStrictEqual(element, item),
+ this.deepStrictEqual(
+ {
+ ...imprt,
+ location: `${imprt.location}.js`,
+ },
+ item,
+ ),
+ ).length === 0 &&
+ imports.filter(imprt =>
+ imprt.unnamedDefault
+ ? this.deepStrictEqual(
+ {
+ location: `${imprt.location}${path.sep}index.js`,
+ unnamedDefault: true,
+ },
+ {
+ location: item.location,
+ unnamedDefault: item.unnamedDefault,
+ },
+ )
+ : this.deepStrictEqual(
+ {
+ ...imprt,
+ location: `${imprt.location}${path.sep}index.js`,
+ },
+ item,
+ ),
).length === 0
) {
acc.push(item) That's not the best way to write it; this was just my work in progress to patch the way the code currently works. Line 410 in 6486693
const getLocation = location =>
- this.joinPaths(
- this.getDir(extPath).join(path.sep),
- location + this.getExt(extPath),
- )
+ path.join(this.getDir(extPath).join(path.sep), location) A side note: I avoided using Lines 207 to 209 in 6486693
I think namespace imports were not working at the time I abandoned the effort? I'm struggling to remember to be honest it was a few weeks ago. |
Thanks for such an awesome tool!
Our project had a
src/constants/index.js
file with a bunch of named exports.These named exports were imported in components within
src/components
with a specifier something like../constants
, and shrimpit was assuming this means../constants.js
and didn't bother looking for./constants/index.js
like Node.js and other tools do.This resulted in all our constants reporting incorrectly as unused.
The text was updated successfully, but these errors were encountered: