mirror of
https://github.com/denoland/rusty_v8.git
synced 2024-11-21 15:04:33 -05:00
Add support for import assertions (#598)
This commit adds support for import assertions. Major changes include: - removal of "ResolveCallback" (deprecated in V8) in favor of "ModuleResolveCallback" - removal of "HostImportModuleDynamicallyCallback" (deprecated in V8) in favor of "HostImportModuleDynamicallyWithImportAssertionsCallback"
This commit is contained in:
parent
1fb0e9436c
commit
d6be279a06
8 changed files with 194 additions and 41 deletions
|
@ -73,19 +73,24 @@ enum InternalSlots {
|
|||
(isolate->GetNumberOfDataSlots() - 1 - slot)
|
||||
|
||||
// This is an extern C calling convention compatible version of
|
||||
// v8::HostImportModuleDynamicallyCallback
|
||||
typedef v8::Promise* (*v8__HostImportModuleDynamicallyCallback)(
|
||||
// v8::HostImportModuleDynamicallyWithImportAssertionsCallback
|
||||
typedef v8::Promise* (
|
||||
*v8__HostImportModuleDynamicallyWithImportAssertionsCallback)(
|
||||
v8::Local<v8::Context> context, v8::Local<v8::ScriptOrModule> referrer,
|
||||
v8::Local<v8::String> specifier);
|
||||
v8::Local<v8::String> specifier,
|
||||
v8::Local<v8::FixedArray> import_assertions);
|
||||
|
||||
v8::MaybeLocal<v8::Promise> HostImportModuleDynamicallyCallback(
|
||||
v8::MaybeLocal<v8::Promise>
|
||||
HostImportModuleDynamicallyWithImportAssertionsCallback(
|
||||
v8::Local<v8::Context> context, v8::Local<v8::ScriptOrModule> referrer,
|
||||
v8::Local<v8::String> specifier) {
|
||||
v8::Local<v8::String> specifier,
|
||||
v8::Local<v8::FixedArray> import_assertions) {
|
||||
auto* isolate = context->GetIsolate();
|
||||
void* d = isolate->GetData(SLOT_INTERNAL(isolate, kSlotDynamicImport));
|
||||
auto* callback = reinterpret_cast<v8__HostImportModuleDynamicallyCallback>(d);
|
||||
auto* callback = reinterpret_cast<
|
||||
v8__HostImportModuleDynamicallyWithImportAssertionsCallback>(d);
|
||||
assert(callback != nullptr);
|
||||
auto* promise_ptr = callback(context, referrer, specifier);
|
||||
auto* promise_ptr = callback(context, referrer, specifier, import_assertions);
|
||||
if (promise_ptr == nullptr) {
|
||||
return v8::MaybeLocal<v8::Promise>();
|
||||
} else {
|
||||
|
@ -221,11 +226,12 @@ void v8__Isolate__SetHostInitializeImportMetaObjectCallback(
|
|||
}
|
||||
|
||||
void v8__Isolate__SetHostImportModuleDynamicallyCallback(
|
||||
v8::Isolate* isolate, v8__HostImportModuleDynamicallyCallback callback) {
|
||||
v8::Isolate* isolate,
|
||||
v8__HostImportModuleDynamicallyWithImportAssertionsCallback callback) {
|
||||
isolate->SetData(SLOT_INTERNAL(isolate, kSlotDynamicImport),
|
||||
reinterpret_cast<void*>(callback));
|
||||
isolate->SetHostImportModuleDynamicallyCallback(
|
||||
HostImportModuleDynamicallyCallback);
|
||||
HostImportModuleDynamicallyWithImportAssertionsCallback);
|
||||
}
|
||||
|
||||
bool v8__Isolate__AddMessageListener(v8::Isolate* isolate,
|
||||
|
@ -614,6 +620,13 @@ const v8::Boolean* v8__Boolean__New(v8::Isolate* isolate, bool value) {
|
|||
return local_to_ptr(v8::Boolean::New(isolate, value));
|
||||
}
|
||||
|
||||
int v8__FixedArray__Length(const v8::FixedArray& self) { return self.Length(); }
|
||||
|
||||
const v8::Data* v8__FixedArray__Get(const v8::FixedArray& self,
|
||||
const v8::Context& context, int index) {
|
||||
return local_to_ptr(ptr_to_local(&self)->Get(ptr_to_local(&context), index));
|
||||
}
|
||||
|
||||
const v8::PrimitiveArray* v8__PrimitiveArray__New(v8::Isolate* isolate,
|
||||
int length) {
|
||||
return local_to_ptr(v8::PrimitiveArray::New(isolate, length));
|
||||
|
@ -1560,18 +1573,15 @@ const v8::Value* v8__Script__Run(const v8::Script& script,
|
|||
}
|
||||
|
||||
void v8__ScriptOrigin__CONSTRUCT(
|
||||
v8::Isolate* isolate,
|
||||
uninit_t<v8::ScriptOrigin>* buf, const v8::Value& resource_name,
|
||||
int resource_line_offset, int resource_column_offset,
|
||||
bool resource_is_shared_cross_origin, int script_id,
|
||||
const v8::Value& source_map_url,
|
||||
bool resource_is_opaque, bool is_wasm, bool is_module) {
|
||||
v8::Isolate* isolate, uninit_t<v8::ScriptOrigin>* buf,
|
||||
const v8::Value& resource_name, int resource_line_offset,
|
||||
int resource_column_offset, bool resource_is_shared_cross_origin,
|
||||
int script_id, const v8::Value& source_map_url, bool resource_is_opaque,
|
||||
bool is_wasm, bool is_module) {
|
||||
construct_in_place<v8::ScriptOrigin>(
|
||||
buf, isolate, ptr_to_local(&resource_name),
|
||||
resource_line_offset, resource_column_offset,
|
||||
resource_is_shared_cross_origin, script_id,
|
||||
ptr_to_local(&source_map_url),
|
||||
resource_is_opaque, is_wasm, is_module);
|
||||
buf, isolate, ptr_to_local(&resource_name), resource_line_offset,
|
||||
resource_column_offset, resource_is_shared_cross_origin, script_id,
|
||||
ptr_to_local(&source_map_url), resource_is_opaque, is_wasm, is_module);
|
||||
}
|
||||
|
||||
const v8::Value* v8__ScriptOrModule__GetResourceName(
|
||||
|
@ -2055,7 +2065,7 @@ int v8__Module__ScriptId(const v8::Module& self) {
|
|||
|
||||
MaybeBool v8__Module__InstantiateModule(const v8::Module& self,
|
||||
const v8::Context& context,
|
||||
v8::Module::ResolveCallback cb) {
|
||||
v8::Module::ResolveModuleCallback cb) {
|
||||
return maybe_to_maybe_bool(
|
||||
ptr_to_local(&self)->InstantiateModule(ptr_to_local(&context), cb));
|
||||
}
|
||||
|
|
11
src/data.rs
11
src/data.rs
|
@ -356,6 +356,17 @@ impl_eq! { for Module }
|
|||
impl_partial_eq! { Data for Module use identity }
|
||||
impl_partial_eq! { Module for Module use identity }
|
||||
|
||||
/// A fixed-sized array with elements of type Data.
|
||||
#[repr(C)]
|
||||
#[derive(Debug)]
|
||||
pub struct FixedArray(Opaque);
|
||||
|
||||
impl_deref! { Data for FixedArray }
|
||||
impl_eq! { for FixedArray }
|
||||
impl_hash! { for FixedArray }
|
||||
impl_partial_eq! { Data for FixedArray use identity }
|
||||
impl_partial_eq! { FixedArray for FixedArray use identity }
|
||||
|
||||
/// An array to hold Primitive values. This is used by the embedder to
|
||||
/// pass host defined options to the ScriptOptions during compilation.
|
||||
///
|
||||
|
|
39
src/fixed_array.rs
Normal file
39
src/fixed_array.rs
Normal file
|
@ -0,0 +1,39 @@
|
|||
// Copyright 2019-2020 the Deno authors. All rights reserved. MIT license.
|
||||
use crate::support::int;
|
||||
use crate::Context;
|
||||
use crate::Data;
|
||||
use crate::FixedArray;
|
||||
use crate::HandleScope;
|
||||
use crate::Local;
|
||||
|
||||
extern "C" {
|
||||
fn v8__FixedArray__Length(this: *const FixedArray) -> int;
|
||||
|
||||
fn v8__FixedArray__Get(
|
||||
this: *const FixedArray,
|
||||
context: *const Context,
|
||||
index: int,
|
||||
) -> *const Data;
|
||||
}
|
||||
|
||||
impl FixedArray {
|
||||
pub fn length(&self) -> usize {
|
||||
unsafe { v8__FixedArray__Length(self) as usize }
|
||||
}
|
||||
|
||||
pub fn get<'s>(
|
||||
&self,
|
||||
scope: &mut HandleScope<'s>,
|
||||
index: usize,
|
||||
) -> Option<Local<'s, Data>> {
|
||||
if index >= self.length() {
|
||||
return None;
|
||||
}
|
||||
|
||||
unsafe {
|
||||
scope.cast_local(|sd| {
|
||||
v8__FixedArray__Get(self, &*sd.get_current_context(), index as int)
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
|
@ -11,6 +11,7 @@ use crate::support::UnitType;
|
|||
use crate::wasm::trampoline;
|
||||
use crate::wasm::WasmStreaming;
|
||||
use crate::Context;
|
||||
use crate::FixedArray;
|
||||
use crate::Function;
|
||||
use crate::Local;
|
||||
use crate::Message;
|
||||
|
@ -90,7 +91,7 @@ pub type PromiseRejectCallback = extern "C" fn(PromiseRejectMessage);
|
|||
pub type HostInitializeImportMetaObjectCallback =
|
||||
extern "C" fn(Local<Context>, Local<Module>, Local<Object>);
|
||||
|
||||
/// HostImportModuleDynamicallyCallback is called when we require the
|
||||
/// HostImportModuleDynamicallyWithImportAssertionsCallback is called when we require the
|
||||
/// embedder to load a module. This is used as part of the dynamic
|
||||
/// import syntax.
|
||||
///
|
||||
|
@ -108,11 +109,13 @@ pub type HostInitializeImportMetaObjectCallback =
|
|||
/// this promise with the exception. If the promise creation itself
|
||||
/// fails (e.g. due to stack overflow), the embedder must propagate
|
||||
/// that exception by returning an empty MaybeLocal.
|
||||
pub type HostImportModuleDynamicallyCallback = extern "C" fn(
|
||||
Local<Context>,
|
||||
Local<ScriptOrModule>,
|
||||
Local<String>,
|
||||
) -> *mut Promise;
|
||||
pub type HostImportModuleDynamicallyWithImportAssertionsCallback =
|
||||
extern "C" fn(
|
||||
Local<Context>,
|
||||
Local<ScriptOrModule>,
|
||||
Local<String>,
|
||||
Local<FixedArray>,
|
||||
) -> *mut Promise;
|
||||
|
||||
pub type InterruptCallback =
|
||||
extern "C" fn(isolate: &mut Isolate, data: *mut c_void);
|
||||
|
@ -180,7 +183,7 @@ extern "C" {
|
|||
);
|
||||
fn v8__Isolate__SetHostImportModuleDynamicallyCallback(
|
||||
isolate: *mut Isolate,
|
||||
callback: HostImportModuleDynamicallyCallback,
|
||||
callback: HostImportModuleDynamicallyWithImportAssertionsCallback,
|
||||
);
|
||||
fn v8__Isolate__RequestInterrupt(
|
||||
isolate: *const Isolate,
|
||||
|
@ -507,7 +510,7 @@ impl Isolate {
|
|||
/// import() language feature to load modules.
|
||||
pub fn set_host_import_module_dynamically_callback(
|
||||
&mut self,
|
||||
callback: HostImportModuleDynamicallyCallback,
|
||||
callback: HostImportModuleDynamicallyWithImportAssertionsCallback,
|
||||
) {
|
||||
unsafe {
|
||||
v8__Isolate__SetHostImportModuleDynamicallyCallback(self, callback)
|
||||
|
|
|
@ -192,6 +192,7 @@ pub(crate) mod raw {
|
|||
pub embedder_wrapper_type_index: int,
|
||||
pub embedder_wrapper_object_index: int,
|
||||
pub cpp_heap_params: SharedPtr<CppHeapCreateParams>,
|
||||
// NOTE(bartlomieju): this field is deprecated in V8 API.
|
||||
// This is an std::vector<std::string>. It's usually no bigger
|
||||
// than three or four words but let's take a generous upper bound.
|
||||
pub supported_import_assertions: [usize; 8],
|
||||
|
|
|
@ -42,6 +42,7 @@ mod date;
|
|||
mod exception;
|
||||
mod external;
|
||||
mod external_references;
|
||||
mod fixed_array;
|
||||
mod function;
|
||||
mod handle;
|
||||
mod isolate;
|
||||
|
@ -92,7 +93,7 @@ pub use handle::Global;
|
|||
pub use handle::Handle;
|
||||
pub use handle::Local;
|
||||
pub use isolate::HeapStatistics;
|
||||
pub use isolate::HostImportModuleDynamicallyCallback;
|
||||
pub use isolate::HostImportModuleDynamicallyWithImportAssertionsCallback;
|
||||
pub use isolate::HostInitializeImportMetaObjectCallback;
|
||||
pub use isolate::Isolate;
|
||||
pub use isolate::IsolateHandle;
|
||||
|
|
|
@ -11,6 +11,7 @@ use crate::support::MaybeBool;
|
|||
use crate::support::ToCFn;
|
||||
use crate::support::UnitType;
|
||||
use crate::Context;
|
||||
use crate::FixedArray;
|
||||
use crate::HandleScope;
|
||||
use crate::Isolate;
|
||||
use crate::Local;
|
||||
|
@ -19,7 +20,7 @@ use crate::String;
|
|||
use crate::Value;
|
||||
|
||||
/// Called during Module::instantiate_module. Provided with arguments:
|
||||
/// (context, specifier, referrer). Return None on error.
|
||||
/// (context, specifier, import_assertions, referrer). Return None on error.
|
||||
///
|
||||
/// Note: this callback has an unusual signature due to ABI incompatibilities
|
||||
/// between Rust and C++. However end users can implement the callback as
|
||||
|
@ -29,6 +30,7 @@ use crate::Value;
|
|||
/// fn my_resolve_callback<'a>(
|
||||
/// context: v8::Local<'a, v8::Context>,
|
||||
/// specifier: v8::Local<'a, v8::String>,
|
||||
/// import_assertions: v8::Local<'a, v8::FixedArray>,
|
||||
/// referrer: v8::Local<'a, v8::Module>,
|
||||
/// ) -> Option<v8::Local<'a, v8::Module>> {
|
||||
/// // ...
|
||||
|
@ -38,34 +40,37 @@ use crate::Value;
|
|||
|
||||
// System V AMD64 ABI: Local<Module> returned in a register.
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
pub type ResolveCallback<'a> = extern "C" fn(
|
||||
pub type ResolveModuleCallback<'a> = extern "C" fn(
|
||||
Local<'a, Context>,
|
||||
Local<'a, String>,
|
||||
Local<'a, FixedArray>,
|
||||
Local<'a, Module>,
|
||||
) -> *const Module;
|
||||
|
||||
// Windows x64 ABI: Local<Module> returned on the stack.
|
||||
#[cfg(target_os = "windows")]
|
||||
pub type ResolveCallback<'a> = extern "C" fn(
|
||||
pub type ResolveModuleCallback<'a> = extern "C" fn(
|
||||
*mut *const Module,
|
||||
Local<'a, Context>,
|
||||
Local<'a, String>,
|
||||
Local<'a, FixedArray>,
|
||||
Local<'a, Module>,
|
||||
) -> *mut *const Module;
|
||||
|
||||
impl<'a, F> MapFnFrom<F> for ResolveCallback<'a>
|
||||
impl<'a, F> MapFnFrom<F> for ResolveModuleCallback<'a>
|
||||
where
|
||||
F: UnitType
|
||||
+ Fn(
|
||||
Local<'a, Context>,
|
||||
Local<'a, String>,
|
||||
Local<'a, FixedArray>,
|
||||
Local<'a, Module>,
|
||||
) -> Option<Local<'a, Module>>,
|
||||
{
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
fn mapping() -> Self {
|
||||
let f = |context, specifier, referrer| {
|
||||
(F::get())(context, specifier, referrer)
|
||||
let f = |context, specifier, import_assertions, referrer| {
|
||||
(F::get())(context, specifier, import_assertions, referrer)
|
||||
.map(|r| -> *const Module { &*r })
|
||||
.unwrap_or(null())
|
||||
};
|
||||
|
@ -74,8 +79,8 @@ where
|
|||
|
||||
#[cfg(target_os = "windows")]
|
||||
fn mapping() -> Self {
|
||||
let f = |ret_ptr, context, specifier, referrer| {
|
||||
let r = (F::get())(context, specifier, referrer)
|
||||
let f = |ret_ptr, context, specifier, import_assertions, referrer| {
|
||||
let r = (F::get())(context, specifier, import_assertions, referrer)
|
||||
.map(|r| -> *const Module { &*r })
|
||||
.unwrap_or(null());
|
||||
unsafe { std::ptr::write(ret_ptr, r) }; // Write result to stack.
|
||||
|
@ -144,7 +149,7 @@ extern "C" {
|
|||
fn v8__Module__InstantiateModule(
|
||||
this: *const Module,
|
||||
context: *const Context,
|
||||
cb: ResolveCallback,
|
||||
cb: ResolveModuleCallback,
|
||||
) -> MaybeBool;
|
||||
fn v8__Module__Evaluate(
|
||||
this: *const Module,
|
||||
|
@ -283,7 +288,7 @@ impl Module {
|
|||
pub fn instantiate_module<'a>(
|
||||
&self,
|
||||
scope: &mut HandleScope,
|
||||
callback: impl MapFnTo<ResolveCallback<'a>>,
|
||||
callback: impl MapFnTo<ResolveModuleCallback<'a>>,
|
||||
) -> Option<bool> {
|
||||
unsafe {
|
||||
v8__Module__InstantiateModule(
|
||||
|
|
|
@ -34,7 +34,7 @@ fn setup() -> SetupGuard {
|
|||
let mut g = INIT_LOCK.lock().unwrap();
|
||||
*g += 1;
|
||||
if *g == 1 {
|
||||
v8::V8::set_flags_from_string("--expose_gc");
|
||||
v8::V8::set_flags_from_string("--expose_gc --harmony-import-assertions");
|
||||
v8::V8::initialize_platform(v8::new_default_platform().unwrap());
|
||||
v8::V8::initialize();
|
||||
}
|
||||
|
@ -913,6 +913,7 @@ fn add_message_listener() {
|
|||
fn unexpected_module_resolve_callback<'a>(
|
||||
_context: v8::Local<'a, v8::Context>,
|
||||
_specifier: v8::Local<'a, v8::String>,
|
||||
_import_assertions: v8::Local<'a, v8::FixedArray>,
|
||||
_referrer: v8::Local<'a, v8::Module>,
|
||||
) -> Option<v8::Local<'a, v8::Module>> {
|
||||
unreachable!()
|
||||
|
@ -1980,6 +1981,7 @@ fn module_instantiation_failures1() {
|
|||
fn resolve_callback<'a>(
|
||||
context: v8::Local<'a, v8::Context>,
|
||||
_specifier: v8::Local<'a, v8::String>,
|
||||
_import_assertions: v8::Local<'a, v8::FixedArray>,
|
||||
_referrer: v8::Local<'a, v8::Module>,
|
||||
) -> Option<v8::Local<'a, v8::Module>> {
|
||||
let scope = &mut unsafe { v8::CallbackScope::new(context) };
|
||||
|
@ -2003,6 +2005,7 @@ fn module_instantiation_failures1() {
|
|||
fn compile_specifier_as_module_resolve_callback<'a>(
|
||||
context: v8::Local<'a, v8::Context>,
|
||||
specifier: v8::Local<'a, v8::String>,
|
||||
_import_assertions: v8::Local<'a, v8::FixedArray>,
|
||||
_referrer: v8::Local<'a, v8::Module>,
|
||||
) -> Option<v8::Local<'a, v8::Module>> {
|
||||
let scope = &mut unsafe { v8::CallbackScope::new(context) };
|
||||
|
@ -2053,6 +2056,85 @@ fn module_evaluation() {
|
|||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn import_assertions() {
|
||||
let _setup_guard = setup();
|
||||
let isolate = &mut v8::Isolate::new(Default::default());
|
||||
|
||||
fn module_resolve_callback<'a>(
|
||||
context: v8::Local<'a, v8::Context>,
|
||||
_specifier: v8::Local<'a, v8::String>,
|
||||
import_assertions: v8::Local<'a, v8::FixedArray>,
|
||||
_referrer: v8::Local<'a, v8::Module>,
|
||||
) -> Option<v8::Local<'a, v8::Module>> {
|
||||
let scope = &mut unsafe { v8::CallbackScope::new(context) };
|
||||
|
||||
// "type" keyword, value and source offset of assertion
|
||||
assert_eq!(import_assertions.length(), 3);
|
||||
let assert1 = import_assertions.get(scope, 0).unwrap();
|
||||
let assert1_val = v8::Local::<v8::Value>::try_from(assert1).unwrap();
|
||||
assert_eq!(assert1_val.to_rust_string_lossy(scope), "type");
|
||||
let assert2 = import_assertions.get(scope, 1).unwrap();
|
||||
let assert2_val = v8::Local::<v8::Value>::try_from(assert2).unwrap();
|
||||
assert_eq!(assert2_val.to_rust_string_lossy(scope), "json");
|
||||
let assert3 = import_assertions.get(scope, 2).unwrap();
|
||||
let assert3_val = v8::Local::<v8::Value>::try_from(assert3).unwrap();
|
||||
assert_eq!(assert3_val.to_rust_string_lossy(scope), "27");
|
||||
|
||||
let origin = mock_script_origin(scope, "module.js");
|
||||
let src = v8::String::new(scope, "export const a = 'a';").unwrap();
|
||||
let source = v8::script_compiler::Source::new(src, &origin);
|
||||
let module = v8::script_compiler::compile_module(scope, source).unwrap();
|
||||
Some(module)
|
||||
}
|
||||
|
||||
extern "C" fn dynamic_import_cb(
|
||||
context: v8::Local<v8::Context>,
|
||||
_referrer: v8::Local<v8::ScriptOrModule>,
|
||||
_specifier: v8::Local<v8::String>,
|
||||
import_assertions: v8::Local<v8::FixedArray>,
|
||||
) -> *mut v8::Promise {
|
||||
let scope = &mut unsafe { v8::CallbackScope::new(context) };
|
||||
let scope = &mut v8::HandleScope::new(scope);
|
||||
// "type" keyword, value
|
||||
assert_eq!(import_assertions.length(), 2);
|
||||
let assert1 = import_assertions.get(scope, 0).unwrap();
|
||||
let assert1_val = v8::Local::<v8::Value>::try_from(assert1).unwrap();
|
||||
assert_eq!(assert1_val.to_rust_string_lossy(scope), "type");
|
||||
let assert2 = import_assertions.get(scope, 1).unwrap();
|
||||
let assert2_val = v8::Local::<v8::Value>::try_from(assert2).unwrap();
|
||||
assert_eq!(assert2_val.to_rust_string_lossy(scope), "json");
|
||||
std::ptr::null_mut()
|
||||
}
|
||||
isolate.set_host_import_module_dynamically_callback(dynamic_import_cb);
|
||||
|
||||
{
|
||||
let scope = &mut v8::HandleScope::new(isolate);
|
||||
let context = v8::Context::new(scope);
|
||||
let scope = &mut v8::ContextScope::new(scope, context);
|
||||
|
||||
let source_text = v8::String::new(
|
||||
scope,
|
||||
"import 'foo.json' assert { type: \"json\" };\n\
|
||||
import('foo.json', { assert: { type: 'json' } });",
|
||||
)
|
||||
.unwrap();
|
||||
let origin = mock_script_origin(scope, "foo.js");
|
||||
let source = v8::script_compiler::Source::new(source_text, &origin);
|
||||
|
||||
let module = v8::script_compiler::compile_module(scope, source).unwrap();
|
||||
assert!(module.script_id().is_some());
|
||||
assert!(module.is_source_text_module());
|
||||
assert!(!module.is_synthetic_module());
|
||||
assert_eq!(v8::ModuleStatus::Uninstantiated, module.get_status());
|
||||
module.hash(&mut DefaultHasher::new()); // Should not crash.
|
||||
|
||||
let result = module.instantiate_module(scope, module_resolve_callback);
|
||||
assert!(result.unwrap());
|
||||
assert_eq!(v8::ModuleStatus::Instantiated, module.get_status());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn primitive_array() {
|
||||
let _setup_guard = setup();
|
||||
|
@ -2550,6 +2632,7 @@ fn dynamic_import() {
|
|||
context: v8::Local<v8::Context>,
|
||||
_referrer: v8::Local<v8::ScriptOrModule>,
|
||||
specifier: v8::Local<v8::String>,
|
||||
_import_assertions: v8::Local<v8::FixedArray>,
|
||||
) -> *mut v8::Promise {
|
||||
let scope = &mut unsafe { v8::CallbackScope::new(context) };
|
||||
let scope = &mut v8::HandleScope::new(scope);
|
||||
|
|
Loading…
Reference in a new issue