summaryrefslogtreecommitdiff
path: root/core
diff options
context:
space:
mode:
authorBartek IwaƄczuk <biwanczuk@gmail.com>2022-07-18 20:05:26 +0200
committerGitHub <noreply@github.com>2022-07-18 20:05:26 +0200
commit999cbfb52bc42c58467e3592d5fead9c4ee8a2c1 (patch)
tree5f5336420b675e15cfaa44cf205171623a3f4ab1 /core
parent0d73eb3dd91b5b34bb6c38a25a4e6aac411d38f3 (diff)
feat: import.meta.resolve() (#15074)
This commit adds new "import.meta.resolve()" API which allows to resolve specifiers relative to the module the API is called in. This API supports resolving using import maps.
Diffstat (limited to 'core')
-rw-r--r--core/bindings.rs41
1 files changed, 41 insertions, 0 deletions
diff --git a/core/bindings.rs b/core/bindings.rs
index a88e54af7..f9fd1f402 100644
--- a/core/bindings.rs
+++ b/core/bindings.rs
@@ -271,6 +271,47 @@ pub extern "C" fn host_initialize_import_meta_object_callback(
let main_key = v8::String::new(scope, "main").unwrap();
let main_val = v8::Boolean::new(scope, info.main);
meta.create_data_property(scope, main_key.into(), main_val.into());
+
+ let builder =
+ v8::FunctionBuilder::new(import_meta_resolve).data(url_val.into());
+ let val = v8::FunctionBuilder::<v8::Function>::build(builder, scope).unwrap();
+ let resolve_key = v8::String::new(scope, "resolve").unwrap();
+ meta.set(scope, resolve_key.into(), val.into());
+}
+
+fn import_meta_resolve(
+ scope: &mut v8::HandleScope,
+ args: v8::FunctionCallbackArguments,
+ mut rv: v8::ReturnValue,
+) {
+ if args.length() > 1 {
+ return throw_type_error(scope, "Invalid arguments");
+ }
+
+ let maybe_arg_str = args.get(0).to_string(scope);
+ if maybe_arg_str.is_none() {
+ return throw_type_error(scope, "Invalid arguments");
+ }
+ let specifier = maybe_arg_str.unwrap();
+ let referrer = {
+ let url_prop = args.data().unwrap();
+ url_prop.to_rust_string_lossy(scope)
+ };
+ let module_map_rc = JsRuntime::module_map(scope);
+ let loader = {
+ let module_map = module_map_rc.borrow();
+ module_map.loader.clone()
+ };
+ match loader.resolve(&specifier.to_rust_string_lossy(scope), &referrer, false)
+ {
+ Ok(resolved) => {
+ let resolved_val = serde_v8::to_v8(scope, resolved.as_str()).unwrap();
+ rv.set(resolved_val);
+ }
+ Err(err) => {
+ throw_type_error(scope, &err.to_string());
+ }
+ };
}
pub extern "C" fn promise_reject_callback(message: v8::PromiseRejectMessage) {