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

fix: improved support for cjs and cts modules #26558

Merged
merged 56 commits into from
Nov 1, 2024

Conversation

dsherret
Copy link
Member

@dsherret dsherret commented Oct 25, 2024

Closes #26651
Closes #25498

@dsherret dsherret changed the title fix: cts support fix: improved support for cjs and cts modules Oct 25, 2024
dsherret added a commit that referenced this pull request Oct 28, 2024
@dsherret dsherret marked this pull request as ready for review October 30, 2024 21:33
pub struct ModuleInfoCache {
conn: CacheDB,
parsed_source_cache: Arc<ParsedSourceCache>,
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shifted from being pased along horizontally to being a ctor dependency.

}
}

pub fn analyze_sync(
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This sync version is for the require loader.

// this will conditionally parse because it's using a CapturingModuleParser
parser.parse_module(ParseOptions {
// this will conditionally parse because it's using a CapturingEsParser
parser.parse_program(ParseOptions {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Part of this PR is shifting everything over to using parse_program so that we can quickly tell if a module is definitely an ES module.

@@ -150,42 +147,3 @@ impl deno_graph::ParsedSourceStore for ParsedSourceCache {
}
}
}

pub struct EsmOrCjsChecker {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This was removed and replaced with CjsTracker.

) -> MediaType {
if resolver.in_node_modules(specifier) {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We don't change the media type from stuff like JS to TS when providing it to typescript anymore because this isn't something we can determine at resolution (only when loading). This is fine because we tell typescript about the "node module kind" (if ESM or CJS)

Ok(Cow::Borrowed(path))
}
}
}
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This was moved into the NodeRequireLoader


pub fn url_to_node_resolution(
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

url_to_node_resolution is gone since we no longer determine if something is esm or cjs at resolution time, but rather after loading when we can see if it has imports/exports/tla/etc.

Self { env }
}

pub fn get_closest_package_json(
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All this code was extracted out of other places.

@@ -73,16 +66,14 @@ impl NodeResolutionMode {

#[derive(Debug)]
pub enum NodeResolution {
Esm(Url),
CommonJs(Url),
Module(Url),
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We no longer know this at resolution time.

Cargo.toml Outdated
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm sorry, this PR is hard to split up into multiple smaller ones. There's so much stuff that's intertwined.

The main themes are using "program" more and determining if a js, jsx, ts, or tsx file is cjs or esm always only happens after loading it now.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cc @arnauorriols on these changes and this PR in general. There's now a NodeRequireLoader trait for loading files with require(...) and PackageJsonResolver struct that searches for package.jsons. Let me know if you'd like a walkthrough of the changes.

Copy link
Member

@bartlomieju bartlomieju left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

First pass, ended at cli/resolver.rs because the rest of files doesn't load in the browser :(

cli/args/mod.rs Show resolved Hide resolved
cli/cache/module_info.rs Show resolved Hide resolved
Comment on lines +581 to +582
// todo(dsherret): support in the lsp by stabilizing the feature
// so that we don't have to pipe the config in here
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe link it in an issue so it's not forgotten?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Or the PR that stabilizes it

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The tracking issue has it: #26225 (just updated it to be more clear)

cli/main.rs Show resolved Hide resolved
cli/module_loader.rs Show resolved Hide resolved
cli/module_loader.rs Show resolved Hide resolved
cli/module_loader.rs Show resolved Hide resolved
@@ -53,16 +53,6 @@ pub async fn compile(
);
}

if cli_options.unstable_detect_cjs() {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this on purpose? Shouldn't we land #26439 first?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. It works in deno compile now so I got rid of the warning saying it doesn't work.

})
.unwrap_or(false);
// todo(dsherret): how to avoid cloning here?
Ok(code.to_string())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can make OpLoadResponse accept Arc<str> and then the op_load would return a v8::Array that would manually serialize to v8::String


let source_code = format!(
r#"(function loadCjsModule(moduleName, isMain, inspectBrk) {{
Deno[Deno.internal].node.loadCjsModule(moduleName, isMain, inspectBrk);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

loadCjsModule can probably be removed now. I can do that in a follow up

@dsherret dsherret merged commit 826e42a into denoland:main Nov 1, 2024
17 checks passed
@dsherret dsherret deleted the refactor_handle_program_more branch November 1, 2024 16:27
bartlomieju added a commit that referenced this pull request Nov 5, 2024
* cts support
* better cjs/cts type checking
* deno compile cjs/cts support
* More efficient detect cjs (going towards stabilization)
* Determination of whether .js, .ts, .jsx, or .tsx is cjs or esm is only
done after loading
* Support `import x = require(...);`

Co-authored-by: Bartek Iwańczuk <[email protected]>
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

Successfully merging this pull request may close these issues.

Support for import x = require("...") .cjs extension is supported, but not .cts in version 2 (rc)
2 participants