mdbook/crates/mdbook-core/src/utils/toml_ext.rs
Eric Huss eda77b81db Remove legacy config support
This removes the old legacy config that allowed certain things at the
top level.

The legacy switch was added in https://github.com/rust-lang/mdBook/pull/457

Closes https://github.com/rust-lang/mdBook/issues/2653
2025-08-11 08:25:04 -07:00

94 lines
2.2 KiB
Rust

//! Helper for working with toml types.
use toml::value::{Table, Value};
/// Helper for working with toml types.
pub(crate) trait TomlExt {
/// Read a dotted key.
fn read(&self, key: &str) -> Option<&Value>;
/// Insert with a dotted key.
fn insert(&mut self, key: &str, value: Value);
}
impl TomlExt for Value {
fn read(&self, key: &str) -> Option<&Value> {
if let Some((head, tail)) = split(key) {
self.get(head)?.read(tail)
} else {
self.get(key)
}
}
fn insert(&mut self, key: &str, value: Value) {
if !self.is_table() {
*self = Value::Table(Table::new());
}
let table = self.as_table_mut().expect("unreachable");
if let Some((head, tail)) = split(key) {
table
.entry(head)
.or_insert_with(|| Value::Table(Table::new()))
.insert(tail, value);
} else {
table.insert(key.to_string(), value);
}
}
}
fn split(key: &str) -> Option<(&str, &str)> {
let ix = key.find('.')?;
let (head, tail) = key.split_at(ix);
// splitting will leave the "."
let tail = &tail[1..];
Some((head, tail))
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn read_simple_table() {
let src = "[table]";
let value: Value = toml::from_str(src).unwrap();
let got = value.read("table").unwrap();
assert!(got.is_table());
}
#[test]
fn read_nested_item() {
let src = "[table]\nnested=true";
let value: Value = toml::from_str(src).unwrap();
let got = value.read("table.nested").unwrap();
assert_eq!(got, &Value::Boolean(true));
}
#[test]
fn insert_item_at_top_level() {
let mut value = Value::Table(Table::default());
let item = Value::Boolean(true);
value.insert("first", item.clone());
assert_eq!(value.get("first").unwrap(), &item);
}
#[test]
fn insert_nested_item() {
let mut value = Value::Table(Table::default());
let item = Value::Boolean(true);
value.insert("first.second", item.clone());
let inserted = value.read("first.second").unwrap();
assert_eq!(inserted, &item);
}
}