spin_manifest/
normalize.rsuse std::collections::HashSet;
use crate::schema::v2::{AppManifest, ComponentSpec, KebabId};
pub fn normalize_manifest(manifest: &mut AppManifest) {
normalize_trigger_ids(manifest);
normalize_inline_components(manifest);
}
fn normalize_inline_components(manifest: &mut AppManifest) {
let components = &mut manifest.components;
for trigger in manifest.triggers.values_mut().flatten() {
let trigger_id = &trigger.id;
let component_specs = trigger
.component
.iter_mut()
.chain(
trigger
.components
.values_mut()
.flat_map(|specs| specs.0.iter_mut()),
)
.collect::<Vec<_>>();
let multiple_components = component_specs.len() > 1;
let mut counter = 1;
for spec in component_specs {
if !matches!(spec, ComponentSpec::Inline(_)) {
continue;
};
let inline_id = {
let mut id = KebabId::try_from(format!("{trigger_id}-component"));
if multiple_components
|| id.is_err()
|| components.contains_key(id.as_ref().unwrap())
{
id = Ok(loop {
let id = KebabId::try_from(format!("inline-component{counter}")).unwrap();
if !components.contains_key(&id) {
break id;
}
counter += 1;
});
}
id.unwrap()
};
let inline_spec = std::mem::replace(spec, ComponentSpec::Reference(inline_id.clone()));
let ComponentSpec::Inline(component) = inline_spec else {
unreachable!();
};
components.insert(inline_id.clone(), *component);
}
}
}
fn normalize_trigger_ids(manifest: &mut AppManifest) {
let mut trigger_ids = manifest
.triggers
.values()
.flatten()
.cloned()
.map(|t| t.id)
.collect::<HashSet<_>>();
for (trigger_type, triggers) in &mut manifest.triggers {
let mut counter = 1;
for trigger in triggers {
if !trigger.id.is_empty() {
continue;
}
if let Some(ComponentSpec::Reference(component_id)) = &trigger.component {
let candidate_id = format!("{component_id}-{trigger_type}-trigger");
if !trigger_ids.contains(&candidate_id) {
trigger.id.clone_from(&candidate_id);
trigger_ids.insert(candidate_id);
continue;
}
}
trigger.id = loop {
let id = format!("{trigger_type}-trigger{counter}");
if !trigger_ids.contains(&id) {
trigger_ids.insert(id.clone());
break id;
}
counter += 1;
}
}
}
}