use rolldown_utils::ecmascript::is_validate_assignee_identifier_name;
use serde_json::Value;
pub fn json_to_esm(json: &str) -> serde_json::Result<String> {
let json_value = serde_json::from_str(json.trim_start_matches("\u{FEFF}"))?;
match json_value {
Value::Object(map) => {
let mut source = String::new();
let mut exported_items_for_default_export = Vec::with_capacity(map.len());
for (idx, (key, value)) in map.iter().enumerate() {
if is_validate_assignee_identifier_name(key) {
source
.push_str(&format!("export const {key} = {};\n", serde_json::to_string_pretty(value)?));
exported_items_for_default_export.push(key.to_string());
} else {
let valid_id = format!("key_{}", itoa::Buffer::new().format(idx));
source.push_str(&format!(
"const {} = {};\n",
valid_id,
serde_json::to_string_pretty(value)?
));
source.push_str(&format!("export {{ {valid_id} as '{key}' }};\n"));
exported_items_for_default_export.push(format!("'{key}': {valid_id}"));
};
}
source.push_str(&format!(
"export default {{ {} }};",
exported_items_for_default_export.join(", ")
));
Ok(source)
}
_ => {
let json_str = serde_json::to_string(&json_value)?;
Ok(format!("export default {json_str}"))
}
}
}