use std::collections::{BTreeMap, BTreeSet};
use crate::source::LoadSpec;
pub(super) fn apply_aliases(
tree: &mut crate::resolve::Table,
provenance: &mut BTreeMap<String, crate::Origin>,
collected: &crate::resolve::Collected,
spec: &LoadSpec<'_>,
) -> Result<(), crate::Error> {
let Some(aliases) = spec.aliases else {
return Ok(());
};
let pairs = aliases.pairs();
let mut filled: BTreeSet<&str> = BTreeSet::new();
let mut progressed = true;
let default = crate::Origin::Runtime("default");
while progressed {
progressed = false;
for (from, to) in &pairs {
if filled.contains(to.as_str()) {
continue;
}
if crate::resolve::supplied_beyond(provenance, to, &default) {
continue;
}
let (section, from_path) = crate::aliases::split_section(from);
let found = match section {
Some(section) => {
collected
.sibling(spec.engine(), section)?
.and_then(|(values, origins)| {
crate::resolve::at(&values, from_path)
.cloned()
.map(|value| (value, origins.get(from_path).cloned()))
})
}
None => crate::resolve::at(tree, from_path)
.cloned()
.map(|value| (value, provenance.get(from_path).cloned())),
};
let Some((value, supplier)) = found else {
continue;
};
crate::resolve::assign(
tree,
provenance,
to,
value,
&supplier.unwrap_or(crate::Origin::Unknown),
);
filled.insert(to.as_str());
progressed = true;
}
}
Ok(())
}