From 8eddfcff7b4cdab782eafacd049d3a378aeee6d7 Mon Sep 17 00:00:00 2001 From: ldm0 Date: Wed, 30 Sep 2026 21:33:00 +0800 Subject: [PATCH] fix: reconcile shared module sources and main regressions --- moli-core/tests/scripts.rs | 1 - moli-dom/src/native/queries.rs | 27 ------ .../src/document_module_graph/key.rs | 9 +- moli-renderer-v8/src/module_runtime/graph.rs | 5 +- .../script_vm/native_module/module_graph.rs | 4 +- .../live_document/document_write.rs | 92 ------------------- moli-renderer-v8/src/script_vm/tests/mod.rs | 1 - .../src/worker/thread/tests/postmessage.rs | 14 --- 8 files changed, 11 insertions(+), 142 deletions(-) diff --git a/moli-core/tests/scripts.rs b/moli-core/tests/scripts.rs index efedd37f43..06f5353ab0 100644 --- a/moli-core/tests/scripts.rs +++ b/moli-core/tests/scripts.rs @@ -6798,7 +6798,6 @@ async fn parse_time_lifecycle_queue_can_stop_cleanly_at_load_stage_after_load_mi Ok(()) } - #[path = "scripts/child_markup_insertion.rs"] mod child_markup_insertion; #[path = "scripts/preload_consumption.rs"] diff --git a/moli-dom/src/native/queries.rs b/moli-dom/src/native/queries.rs index 30cdd9aeac..2ce1a1f55e 100644 --- a/moli-dom/src/native/queries.rs +++ b/moli-dom/src/native/queries.rs @@ -335,33 +335,6 @@ impl NativeDom { .map(|document| document.scripting_enabled()) } - pub(crate) fn light_subtree_handles( - &self, - root: NativeNodeId, - include_root: bool, - ) -> impl Iterator + '_ { - let first = self.node(root).and_then(|node| { - if include_root { - Some(root) - } else { - node.first_child() - } - }); - std::iter::successors(first, move |&handle| { - if let Some(child) = self.first_child(handle) { - return Some(child); - } - let mut current = handle; - while current != root { - if let Some(sibling) = self.next_sibling(current) { - return Some(sibling); - } - current = self.parent_node(current)?; - } - None - }) - } - fn collect_matching_elements( &self, root: NativeNodeId, diff --git a/moli-renderer-v8/src/document_module_graph/key.rs b/moli-renderer-v8/src/document_module_graph/key.rs index 0ee0446e08..f61e71a5fe 100644 --- a/moli-renderer-v8/src/document_module_graph/key.rs +++ b/moli-renderer-v8/src/document_module_graph/key.rs @@ -80,10 +80,11 @@ impl ModuleKind { /// Whether the module map still needs the fetched source after compilation. pub(crate) fn retains_source_after_compilation(self) -> bool { match self { - // V8 owns JavaScript source; synthetic text records own JSON/CSS source. - Self::JavaScript | Self::Json | Self::Css => false, - // Preserve the separate source semantics of Wasm and text preloads. - Self::WebAssembly | Self::ModulePreloadText => true, + // V8 owns JavaScript source and parsed JSON/text exports; compiled + // CSS records retain their shared source allocation. + Self::JavaScript | Self::Json | Self::Css | Self::Text => false, + // Wasm source-phase imports still need the original bytes. + Self::WebAssembly => true, } } } diff --git a/moli-renderer-v8/src/module_runtime/graph.rs b/moli-renderer-v8/src/module_runtime/graph.rs index 1ddafad039..856e96d2f4 100644 --- a/moli-renderer-v8/src/module_runtime/graph.rs +++ b/moli-renderer-v8/src/module_runtime/graph.rs @@ -2750,6 +2750,7 @@ mod tests { for (module_type, text) in [ ("json", r#"{"answer":42}"#), ("css", "body { color: red; }"), + ("text", "plain text export"), ] { let mut vm = new_test_vm("https://app.example.test/page"); let source_url = url(&format!("https://app.example.test/source.{module_type}")); @@ -2785,10 +2786,10 @@ mod tests { ); drop(fetched); drop(source); - if module_type == "json" { + if module_type != "css" { assert!( weak_source.upgrade().is_none(), - "parsed JSON modules must release the original source text", + "{module_type}: V8 exports must release the original source text", ); } else { assert_eq!( diff --git a/moli-renderer-v8/src/script_vm/native_module/module_graph.rs b/moli-renderer-v8/src/script_vm/native_module/module_graph.rs index 7c3b1f935a..a982fb04a5 100644 --- a/moli-renderer-v8/src/script_vm/native_module/module_graph.rs +++ b/moli-renderer-v8/src/script_vm/native_module/module_graph.rs @@ -71,7 +71,9 @@ impl ScriptVm { ) } ModuleKind::Json | ModuleKind::Css | ModuleKind::Text => { - let ModuleSource::Text(source) = source else { + let (ModuleSource::Text(source) | ModuleSource::TextWithOrigin { source, .. }) = + source + else { return Err(ModuleLoadError::new( ModuleLoadStage::Compile, format!("synthetic text module `{source_url}` did not retain text source"), diff --git a/moli-renderer-v8/src/script_vm/tests/dom_elements/live_document/document_write.rs b/moli-renderer-v8/src/script_vm/tests/dom_elements/live_document/document_write.rs index 8639a0d4e3..af3fa628f4 100644 --- a/moli-renderer-v8/src/script_vm/tests/dom_elements/live_document/document_write.rs +++ b/moli-renderer-v8/src/script_vm/tests/dom_elements/live_document/document_write.rs @@ -394,57 +394,6 @@ fn document_open_resets_compat_mode_and_parser_updates_it_incrementally() { ); } -#[test] -fn child_document_open_resets_compat_mode_before_doctype_or_eof() { - let mut vm = new_parsed_test_vm( - "https://child-document-open-quirks.test/", - "parent", - ); - let result = vm - .eval( - r#" -(() => { - const f = document.body.appendChild(document.createElement('iframe')); - const d = f.contentDocument; - const rows = []; - for (const chunks of [ - [], - [''], - [''], - ['', 'quirks'], - [''] - ]) { - const modes = [d.compatMode]; - d.open(); - modes.push(d.compatMode); - for (const chunk of chunks) { - d.write(chunk); - modes.push(d.compatMode); - } - d.close(); - modes.push(d.compatMode); - rows.push(modes.join('|')); - } - f.remove(); - return rows.join('\n'); -})() -"#, - ) - .unwrap(); - assert_eq!( - result, - [ - "BackCompat|CSS1Compat|BackCompat", - "BackCompat|CSS1Compat|CSS1Compat|CSS1Compat|BackCompat|BackCompat", - "BackCompat|CSS1Compat|CSS1Compat|CSS1Compat|CSS1Compat", - "CSS1Compat|CSS1Compat|CSS1Compat|BackCompat|BackCompat", - "BackCompat|CSS1Compat|CSS1Compat|CSS1Compat", - ] - .join("\n") - ); - assert_eq!(vm.eval("document.compatMode").unwrap(), "CSS1Compat"); -} - #[test] fn child_document_open_initializes_native_no_quirks_mode() { for open in ["d.open()", "d.write('quirks parent", - ); - vm.eval(&format!( - r#" -const f = document.body.appendChild(document.createElement('iframe')); -f.id = 'mode-frame'; -const d = f.contentDocument; -{open}; -const html = d.appendChild(d.createElement('html')); -html.appendChild(d.createElement('body')); -d.body.innerHTML = '

child

'; -"# - )) - .unwrap(); - assert_eq!( - vm.eval("JSON.stringify([d.compatMode, d.querySelectorAll('.upper').length, document.compatMode])") - .unwrap(), - r#"["CSS1Compat",0,"BackCompat"]"#, - "{open}" - ); - let host = vm._context_host.borrow(); - let frame = host.dom_host().element_handle_by_id("mode-frame").unwrap(); - let document = host.child_browsing_context_document_handle(frame).unwrap(); - assert_eq!( - host.dom_host() - .node(document) - .unwrap() - .as_document() - .unwrap() - .quirks_mode(), - selectors::matching::QuirksMode::NoQuirks, - "{open}: native mode must not be limited-quirks" - ); - } -} diff --git a/moli-renderer-v8/src/script_vm/tests/mod.rs b/moli-renderer-v8/src/script_vm/tests/mod.rs index 9355555df3..0bb0376aec 100644 --- a/moli-renderer-v8/src/script_vm/tests/mod.rs +++ b/moli-renderer-v8/src/script_vm/tests/mod.rs @@ -2331,7 +2331,6 @@ mod window_cross_origin_getters; mod window_event_receivers; mod window_execution_context; mod window_getter_consolidation; -mod worklet_interfaces; mod payment_response_interfaces; mod body_mime_consolidation; diff --git a/moli-renderer-v8/src/worker/thread/tests/postmessage.rs b/moli-renderer-v8/src/worker/thread/tests/postmessage.rs index ba8baf6411..cfbe149d72 100644 --- a/moli-renderer-v8/src/worker/thread/tests/postmessage.rs +++ b/moli-renderer-v8/src/worker/thread/tests/postmessage.rs @@ -3604,20 +3604,6 @@ async fn worker_does_not_expose_window_worklet_interfaces() { ); } -#[tokio::test] -async fn worker_does_not_expose_window_media_device_interfaces() { - ensure_v8(); - let mut handle = spawn_worker("postMessage({MediaDeviceInfo:'MediaDeviceInfo' in self,InputDeviceInfo:'InputDeviceInfo' in self});close();".to_owned(), "https://media-device-worker.test/worker.js".into()); - let message = timeout(TIMEOUT, handle.recv()) - .await - .expect("timed out") - .expect("channel closed"); - assert_eq!( - expect_post_json(message), - r#"{"MediaDeviceInfo":false,"InputDeviceInfo":false}"# - ); -} - #[tokio::test] async fn worker_does_not_expose_window_audio_node_interface() { ensure_v8();