From fca41ab42e913082ae4158f06b2b5613b6431d8e Mon Sep 17 00:00:00 2001 From: overlookmotel Date: Wed, 21 Aug 2024 11:51:29 +0100 Subject: [PATCH] fix(semantic): transform checker handle conditional scopes --- .../src/post_transform_checker.rs | 65 ++++++++++++------- tasks/transform_conformance/babel.snap.md | 24 ++++++- tasks/transform_conformance/oxc.snap.md | 24 ++++++- 3 files changed, 84 insertions(+), 29 deletions(-) diff --git a/crates/oxc_semantic/src/post_transform_checker.rs b/crates/oxc_semantic/src/post_transform_checker.rs index 13108d8631137..c3d8b67b82152 100644 --- a/crates/oxc_semantic/src/post_transform_checker.rs +++ b/crates/oxc_semantic/src/post_transform_checker.rs @@ -1,4 +1,4 @@ -use std::{cell::Cell, collections::HashSet, mem}; +use std::{cell::Cell, mem}; use oxc_allocator::{Allocator, CloneIn}; #[allow(clippy::wildcard_imports)] @@ -87,28 +87,47 @@ impl PostTransformChecker { } // Check whether bindings are the same for scopes in the same visitation order. - for (prev_scope_id, cur_scope_id) in + for (&prev_scope_id, &cur_scope_id) in self.collect_after_transform.scope_ids.iter().zip(current_collect.scope_ids.iter()) { - let mut prev_bindings = - previous_scopes.get_bindings(*prev_scope_id).keys().cloned().collect::>(); - prev_bindings.sort_unstable(); - let mut current_bindings = - current_scopes.get_bindings(*cur_scope_id).keys().cloned().collect::>(); - current_bindings.sort_unstable(); - - if prev_bindings.iter().collect::>() - != current_bindings.iter().collect::>() - { - let message = format!( - " -Bindings mismatch: -previous {prev_scope_id:?}: {prev_bindings:?} -current {cur_scope_id:?}: {current_bindings:?} - " - ); - self.errors.push(OxcDiagnostic::error(message.trim().to_string())); + fn get_sorted_bindings(scopes: &ScopeTree, scope_id: ScopeId) -> Vec { + let mut bindings = + scopes.get_bindings(scope_id).keys().cloned().collect::>(); + bindings.sort_unstable(); + bindings } + + let (previous, current) = match (prev_scope_id, cur_scope_id) { + (None, None) => continue, + (Some(prev_scope_id), Some(cur_scope_id)) => { + let prev_bindings = get_sorted_bindings(previous_scopes, prev_scope_id); + let current_bindings = get_sorted_bindings(current_scopes, cur_scope_id); + if prev_bindings == current_bindings { + continue; + } + ( + format!("{prev_scope_id:?}: {prev_bindings:?}"), + format!("{cur_scope_id:?}: {current_bindings:?}"), + ) + } + (Some(prev_scope_id), None) => { + let prev_bindings = get_sorted_bindings(previous_scopes, prev_scope_id); + (format!("{prev_scope_id:?}: {prev_bindings:?}"), "No scope".to_string()) + } + (None, Some(cur_scope_id)) => { + let current_bindings = get_sorted_bindings(current_scopes, cur_scope_id); + ("No scope".to_string(), format!("{cur_scope_id:?}: {current_bindings:?}")) + } + }; + + let message = format!( + " +Bindings mismatch: +previous {previous} +current {current} + " + ); + self.errors.push(OxcDiagnostic::error(message.trim().to_string())); } } @@ -209,7 +228,7 @@ current {cur_reference_id:?}: {cur_symbol_name:?} #[derive(Default)] pub struct SemanticCollector { - scope_ids: Vec, + scope_ids: Vec>, symbol_ids: Vec, reference_ids: Vec, @@ -218,9 +237,7 @@ pub struct SemanticCollector { impl<'a> Visit<'a> for SemanticCollector { fn enter_scope(&mut self, _flags: ScopeFlags, scope_id: &Cell>) { - if let Some(scope_id) = scope_id.get() { - self.scope_ids.push(scope_id); - } + self.scope_ids.push(scope_id.get()); } fn visit_identifier_reference(&mut self, ident: &IdentifierReference<'a>) { diff --git a/tasks/transform_conformance/babel.snap.md b/tasks/transform_conformance/babel.snap.md index 9ab3c3a80176a..9ae917120aa58 100644 --- a/tasks/transform_conformance/babel.snap.md +++ b/tasks/transform_conformance/babel.snap.md @@ -1647,11 +1647,31 @@ preset-env: unknown field `shippedProposals`, expected `targets` or `bugfixes` # babel-plugin-transform-optional-catch-binding (2/4) * optional-catch-bindings/try-catch-block-no-binding/input.js - x Scopes mismatch after transform + x Bindings mismatch: + | previous ScopeId(0): ["_unused"] + | current ScopeId(0): [] + + x Bindings mismatch: + | previous No scope + | current ScopeId(2): [] + + x Bindings mismatch: + | previous ScopeId(2): [] + | current ScopeId(3): ["_unused"] * optional-catch-bindings/try-catch-finally-no-binding/input.js - x Scopes mismatch after transform + x Bindings mismatch: + | previous ScopeId(0): ["_unused"] + | current ScopeId(0): [] + + x Bindings mismatch: + | previous No scope + | current ScopeId(2): [] + + x Bindings mismatch: + | previous ScopeId(2): [] + | current ScopeId(3): ["_unused"] diff --git a/tasks/transform_conformance/oxc.snap.md b/tasks/transform_conformance/oxc.snap.md index b24c5481afe39..fdaa2d9747382 100644 --- a/tasks/transform_conformance/oxc.snap.md +++ b/tasks/transform_conformance/oxc.snap.md @@ -8,7 +8,17 @@ Passed: 9/35 # babel-plugin-transform-optional-catch-binding (0/1) * try-catch-shadow/input.js - x Scopes mismatch after transform + x Bindings mismatch: + | previous ScopeId(0): ["_unused", "_unused2"] + | current ScopeId(0): ["_unused"] + + x Bindings mismatch: + | previous No scope + | current ScopeId(2): [] + + x Bindings mismatch: + | previous ScopeId(2): [] + | current ScopeId(3): ["_unused2"] @@ -218,7 +228,9 @@ Passed: 9/35 * refresh/generates-valid-signature-for-exotic-ways-to-call-hooks/input.jsx - x Scopes mismatch after transform + x Bindings mismatch: + | previous No scope + | current ScopeId(3): [] x Reference mismatch: | previous ReferenceId(17): Some("_s2") @@ -234,7 +246,13 @@ Passed: 9/35 * refresh/includes-custom-hooks-into-the-signatures/input.jsx - x Scopes mismatch after transform + x Bindings mismatch: + | previous No scope + | current ScopeId(2): [] + + x Bindings mismatch: + | previous No scope + | current ScopeId(6): [] x Reference mismatch: | previous ReferenceId(10): Some("_s")