use oxc_allocator::Allocator;
use oxc_parser::Parser;
use oxc_span::SourceType;
use vize_carton::FxHashMap;
use super::collector::collect_identifier_rewrites;
use super::helpers::{transform_props_text_based, PROPS_REST_SENTINEL};
use super::PropsDestructuredBindings;
use vize_carton::{profile, String, ToCompactString};
pub fn transform_destructured_props(
source: &str,
destructured: &PropsDestructuredBindings,
) -> String {
if destructured.is_empty() {
return source.to_compact_string();
}
let mut local_to_key: FxHashMap<&str, &str> = FxHashMap::default();
for (key, binding) in &destructured.bindings {
local_to_key.insert(binding.local.as_str(), key.as_str());
}
if let Some(ref rest_id) = destructured.rest_id {
local_to_key.insert(rest_id.as_str(), PROPS_REST_SENTINEL);
}
let allocator = Allocator::default();
let source_type = SourceType::from_path("script.ts").unwrap_or_default();
let ret = profile!(
"atelier.props_destructure.parse",
Parser::new(&allocator, source, source_type).parse()
);
if !ret.panicked {
let mut rewrites: Vec<(usize, usize, String)> = Vec::new();
profile!(
"atelier.props_destructure.collect_rewrites",
collect_identifier_rewrites(&ret.program, source, &local_to_key, &mut rewrites)
);
if !rewrites.is_empty() {
rewrites.sort_by_key(|rewrite| std::cmp::Reverse(rewrite.0));
let mut result = source.to_compact_string();
for (start, end, replacement) in rewrites {
result.replace_range(start..end, &replacement);
}
return result;
}
return source.to_compact_string();
}
profile!(
"atelier.props_destructure.text_fallback",
transform_props_text_based(source, &local_to_key)
)
}